pax_global_header00006660000000000000000000000064145125770510014521gustar00rootroot0000000000000052 comment=f33756c37f1e41041d84018047b14cb394742761 jacoco-0.8.11/000077500000000000000000000000001451257705100130465ustar00rootroot00000000000000jacoco-0.8.11/.appveyor.yml000066400000000000000000000011571451257705100155200ustar00rootroot00000000000000cache: - C:\Users\appveyor\.m2 -> **\pom.xml install: - mkdir .jdk - curl -L "https://api.azul.com/zulu/download/community/v1.0/bundles/latest/binary/?jdk_version=17&ext=zip&os=windows&arch=x86&hw_bitness=64&javafx=false&bundle_type=jdk" -o .jdk/jdk.zip - unzip -d .jdk .jdk/jdk.zip - mv .jdk/*/* .jdk - .jdk\bin\java -version - SET JAVA_HOME=%CD%\.jdk build_script: # generation of Javadocs requires Java <= 6 (https://github.com/jacoco/jacoco/issues/110) - mvn -V -B -e verify -Djdk.version=6 -Dbytecode.version=5 --toolchains=.travis\appveyor-toolchains.xml artifacts: - path: jacoco\target\*.zip jacoco-0.8.11/.azure-pipelines/000077500000000000000000000000001451257705100162405ustar00rootroot00000000000000jacoco-0.8.11/.azure-pipelines/azure-pipelines.yml000066400000000000000000000057271451257705100221120ustar00rootroot00000000000000jobs: - job: strategy: matrix: JDK 5: JDK_VERSION: 5 JDK 6: JDK_VERSION: 6 JDK 7: JDK_VERSION: 7 JDK 8: JDK_VERSION: 8 JDK 9: JDK_VERSION: 9 JDK 10: JDK_VERSION: 10 JDK 11: JDK_VERSION: 11 JDK 11 with ECJ: JDK_VERSION: 11 ECJ: true JDK 12: JDK_VERSION: 12 JDK 13: JDK_VERSION: 13 JDK 14: JDK_VERSION: 14 JDK 15: JDK_VERSION: 15 JDK 16: JDK_VERSION: 16 JDK 17: JDK_VERSION: 17 JDK 17 with ECJ: JDK_VERSION: 17 ECJ: true JDK 18: JDK_VERSION: 18 JDK 19: JDK_VERSION: 19 JDK 20: JDK_VERSION: 20 JDK 20 with ECJ: JDK_VERSION: 20 ECJ: true JDK 21: JDK_VERSION: 21 JDK 22: JDK_VERSION: 22 pool: vmImage: 'ubuntu-20.04' steps: - bash: | set -e url_var=JDK${JDK_VERSION}_URL JDK_URL=${!url_var} mkdir .jdk curl -L $JDK_URL -o .jdk/jdk.tar.gz tar -xzf .jdk/jdk.tar.gz -C .jdk --strip-components 1 .jdk/bin/java -version echo " jdk $JDK_VERSION $JDK_VERSION $PWD/.jdk " > toolchains.xml displayName: Setup JDK - bash: | set -e mkdir .maven curl -L "https://archive.apache.org/dist/maven/maven-3/3.8.3/binaries/apache-maven-3.8.3-bin.tar.gz" -o .maven/maven.tar.gz tar -xzf .maven/maven.tar.gz -C .maven --strip-components 1 displayName: Setup Maven - bash: | if [[ "$JDK_VERSION" -ge "17" ]]; then export JAVA_HOME=$PWD/.jdk else export JAVA_HOME=$JAVA_HOME_17_X64 fi if [[ "$BUILD_SOURCEBRANCH" == "refs/heads/master" && "$JDK_VERSION" == "5" ]]; then .maven/bin/mvn -V -B -e -f org.jacoco.build \ verify -Djdk.version=$JDK_VERSION -Dbytecode.version=$JDK_VERSION \ deploy:deploy -DdeployAtEnd \ --toolchains=toolchains.xml --settings=.azure-pipelines/maven-settings.xml elif [[ "$BUILD_SOURCEBRANCH" == "refs/heads/master" && "$JDK_VERSION" == "11" ]]; then .maven/bin/mvn -V -B -e -f org.jacoco.build \ verify -Djdk.version=$JDK_VERSION -Dbytecode.version=$JDK_VERSION \ sonar:sonar \ --toolchains=toolchains.xml --settings=.azure-pipelines/maven-settings.xml else .maven/bin/mvn -V -B -e \ verify -Djdk.version=$JDK_VERSION -Dbytecode.version=$JDK_VERSION -Decj=${ECJ:-} \ --toolchains=toolchains.xml fi displayName: Build env: SONARQUBE_TOKEN: $(SONARQUBE_TOKEN) SONATYPE_USERNAME: $(SONATYPE_USERNAME) SONATYPE_PASSWORD: $(SONATYPE_PASSWORD) jacoco-0.8.11/.azure-pipelines/maven-settings.xml000066400000000000000000000014561451257705100217340ustar00rootroot00000000000000 sonatype-nexus-snapshots ${env.SONATYPE_USERNAME} ${env.SONATYPE_PASSWORD} SonarCloud https://sonarcloud.io/ default ${env.SONARQUBE_TOKEN} SonarCloud jacoco-0.8.11/.gitattributes000066400000000000000000000002301451257705100157340ustar00rootroot00000000000000*.java text eol=lf *.properties text eol=lf *.html text eol=lf *.css text eol=lf *.js text eol=lf *.xml text eol=lf *.xsl text eol=lf *.dtd text eol=lf jacoco-0.8.11/.github/000077500000000000000000000000001451257705100144065ustar00rootroot00000000000000jacoco-0.8.11/.github/ISSUE_TEMPLATE.md000066400000000000000000000001361451257705100171130ustar00rootroot00000000000000PLEASE USE ONE OF THE FOLLOWING TEMPLATES https://github.com/jacoco/jacoco/issues/new/choose jacoco-0.8.11/.github/ISSUE_TEMPLATE/000077500000000000000000000000001451257705100165715ustar00rootroot00000000000000jacoco-0.8.11/.github/ISSUE_TEMPLATE/1_question.yml000066400000000000000000000017351451257705100214110ustar00rootroot00000000000000name: Question description: Please ask questions at our user forum title: "PLEASE DO NOT USE GITHUB FOR QUESTIONS - CHECK FAQ OR USE FORUM" labels: ["declined: question :x:"] body: - type: markdown attributes: value: | Please understand that we do **not** use the issue tracker for questions. The issue will be closed as invalid. Many questions are already answered in our [FAQ](https://www.jacoco.org/jacoco/trunk/doc/faq.html). Please have a look at our [forum](https://groups.google.com/forum/?fromgroups=#!forum/jacoco) where more questions have been discussed before or ask a new question at the [forum](https://groups.google.com/forum/?fromgroups=#!forum/jacoco). Thank you for keeping our issue tracker clean! - type: checkboxes id: terms attributes: label: No questions answered here options: - label: I understand that no quesions will be answered on this issue tracker required: true jacoco-0.8.11/.github/ISSUE_TEMPLATE/2_bug_report.md000066400000000000000000000015041451257705100215040ustar00rootroot00000000000000--- name: 'Bug report' about: 'Report a bug in JaCoCo' title: labels: 'type: bug :bug:' assignes: --- THIS IS A BUG TRACKER ONLY. FOR QUESTIONS PLEASE CHECK FAQ OR USE FORUM: http://www.jacoco.org/jacoco/trunk/doc/faq.html https://groups.google.com/forum/?fromgroups=#!forum/jacoco Please understand that ISSUES WITHOUT FOLLOWING INFORMATION WILL BE CLOSED WITHOUT COMMENTS! Thank you for filing a useful bug report! ### Steps to reproduce * JaCoCo version: (from right bottom corner of JaCoCo report) * Operating system: * Tool integration: Maven / Ant / CLI / API (for others please report to respective project) * Complete executable reproducer: (e.g. GitHub Repo) * Steps: (what exactly are you doing with the above reproducer?) ### Expected behaviour ### Actual behaviour (In case of exceptions provide FULL STACKTRACE) jacoco-0.8.11/.github/ISSUE_TEMPLATE/3_feature_request.md000066400000000000000000000014271451257705100225440ustar00rootroot00000000000000--- name: 'Feature request' about: 'Suggest a feature for JaCoCo' title: labels: 'type: enhancement' assignes: --- THIS IS A BUG TRACKER ONLY. FOR QUESTIONS PLEASE CHECK FAQ OR USE FORUM: http://www.jacoco.org/jacoco/trunk/doc/faq.html https://groups.google.com/forum/?fromgroups=#!forum/jacoco Please understand that ISSUES WITHOUT FOLLOWING INFORMATION WILL BE CLOSED WITHOUT COMMENTS! Thank you for filling feature request! ### Scenario * JaCoCo version: (from right bottom corner of JaCoCo report) * Operating system: * Tool integration: Maven / Ant / CLI / API (for others please report to respective project) * Description of your use case: (detailed description or executable reproducer, e.g. GitHub repo) ### Current Behaviour ### Wanted Behaviour ### Possible Workarounds jacoco-0.8.11/.gitignore000066400000000000000000000002011451257705100150270ustar00rootroot00000000000000target/ .settings/ !org.jacoco.core/.settings/ !org.jacoco.core.test/.settings/ org.jacoco.agent/src/jacocoagent.jar .idea *.iml jacoco-0.8.11/.travis/000077500000000000000000000000001451257705100144345ustar00rootroot00000000000000jacoco-0.8.11/.travis/appveyor-toolchains.xml000066400000000000000000000010341451257705100211620ustar00rootroot00000000000000 jdk java16 6 oracle C:\Program Files\Java\jdk1.6.0 jacoco-0.8.11/LICENSE.md000066400000000000000000000012411451257705100144500ustar00rootroot00000000000000License ======= Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors The JaCoCo Java Code Coverage Library and all included documentation is made available by Mountainminds GmbH & Co. KG, Munich. Except indicated below, the Content is provided to you under the terms and conditions of the Eclipse Public License Version 2.0 ("EPL"). A copy of the EPL is available at [https://www.eclipse.org/legal/epl-2.0/](https://www.eclipse.org/legal/epl-2.0/). Please visit [http://www.jacoco.org/jacoco/trunk/doc/license.html](http://www.jacoco.org/jacoco/trunk/doc/license.html) for the complete license information including third party licenses and trademarks. jacoco-0.8.11/README.md000066400000000000000000000023121451257705100143230ustar00rootroot00000000000000JaCoCo Java Code Coverage Library ================================= [![Build Status](https://dev.azure.com/jacoco-org/JaCoCo/_apis/build/status/JaCoCo?branchName=master)](https://dev.azure.com/jacoco-org/JaCoCo/_build/latest?definitionId=1&branchName=master) [![Build status](https://ci.appveyor.com/api/projects/status/g28egytv4tb898d7/branch/master?svg=true)](https://ci.appveyor.com/project/JaCoCo/jacoco/branch/master) [![Maven Central](https://img.shields.io/maven-central/v/org.jacoco/jacoco.svg)](http://search.maven.org/#search|ga|1|g%3Aorg.jacoco) JaCoCo is a free Java code coverage library distributed under the Eclipse Public License. Check the [project homepage](http://www.jacoco.org/jacoco) for downloads, documentation and feedback. Please use our [mailing list](https://groups.google.com/forum/?fromgroups=#!forum/jacoco) for questions regarding JaCoCo which are not already covered by the [extensive documentation](http://www.jacoco.org/jacoco/trunk/doc/). Note: We do not answer general questions in the project's issue tracker. Please use our [mailing list](https://groups.google.com/forum/?fromgroups=#!forum/jacoco) for this. ------------------------------------------------------------------------- jacoco-0.8.11/jacoco-maven-plugin.test/000077500000000000000000000000001451257705100176625ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/.project000066400000000000000000000010731451257705100213320ustar00rootroot00000000000000 jacoco-maven-plugin.test org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/jacoco-maven-plugin.test/it/000077500000000000000000000000001451257705100202765ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-halt/000077500000000000000000000000001451257705100240075ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-halt/invoker.properties000066400000000000000000000000341451257705100275770ustar00rootroot00000000000000invoker.buildResult=failure jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-halt/pom.xml000066400000000000000000000036351451257705100253330ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-check-fails-halt @project.groupId@ jacoco-maven-plugin prepare-agent check check CLASS Example METHOD MISSEDCOUNT 0 jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-halt/src/000077500000000000000000000000001451257705100245765ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-halt/src/main/000077500000000000000000000000001451257705100255225ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-halt/src/main/java/000077500000000000000000000000001451257705100264435ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-halt/src/main/java/Example.java000066400000000000000000000012441451257705100307020ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ public class Example { public void sayHello() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-halt/src/test/000077500000000000000000000000001451257705100255555ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-halt/src/test/java/000077500000000000000000000000001451257705100264765ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-halt/src/test/java/ExampleTest.java000066400000000000000000000012571451257705100316010ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-halt/verify.bsh000066400000000000000000000020321451257705100260060ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( "Coverage checks have not been met." ) < 0 ) { throw new RuntimeException( "Coverage checks should not have been met." ); } if ( buildLog.indexOf( "methods missed count is 1, but expected maximum is 0" ) < 0 ) { throw new RuntimeException( "Should have displayed insufficient code coverage messages." ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-no-halt/000077500000000000000000000000001451257705100244215ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-no-halt/pom.xml000066400000000000000000000035521451257705100257430ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-check-fails-no-hault @project.groupId@ jacoco-maven-plugin prepare-agent check check false BUNDLE METHOD MISSEDCOUNT 0 jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-no-halt/src/000077500000000000000000000000001451257705100252105ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-no-halt/src/main/000077500000000000000000000000001451257705100261345ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-no-halt/src/main/java/000077500000000000000000000000001451257705100270555ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-no-halt/src/main/java/Example.java000066400000000000000000000012441451257705100313140ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ public class Example { public void sayHello() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-no-halt/src/test/000077500000000000000000000000001451257705100261675ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-no-halt/src/test/java/000077500000000000000000000000001451257705100271105ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-no-halt/src/test/java/ExampleTest.java000066400000000000000000000012571451257705100322130ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-fails-no-halt/verify.bsh000066400000000000000000000020311451257705100264170ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( "Coverage checks have not been met." ) < 0 ) { throw new RuntimeException( "Coverage checks should not have been met." ); } if ( buildLog.indexOf( "methods missed count is 1, but expected maximum is 0" ) < 0 ) { throw new RuntimeException( "Should have displayed insufficient code coverage messages." ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-passes/000077500000000000000000000000001451257705100232615ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-passes/pom.xml000066400000000000000000000037751451257705100246120ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-check-passes @project.groupId@ jacoco-maven-plugin prepare-agent check check BUNDLE INSTRUCTION COVEREDRATIO 0.90 CLASS MISSEDCOUNT 0 jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-passes/src/000077500000000000000000000000001451257705100240505ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-passes/src/main/000077500000000000000000000000001451257705100247745ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-passes/src/main/java/000077500000000000000000000000001451257705100257155ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-passes/src/main/java/Example.java000066400000000000000000000012441451257705100301540ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ public class Example { public void sayHello() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-passes/src/test/000077500000000000000000000000001451257705100250275ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-passes/src/test/java/000077500000000000000000000000001451257705100257505ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-passes/src/test/java/ExampleTest.java000066400000000000000000000012721451257705100310500ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example().sayHello(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-check-passes/verify.bsh000066400000000000000000000015221451257705100252630ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( "All coverage checks have been met." ) < 0 ) { throw new RuntimeException( "Coverage checks were not met." ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-customize-agent/000077500000000000000000000000001451257705100240265ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-customize-agent/pom.xml000066400000000000000000000050531451257705100253460ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-customize-agent coverageAgent ${project.build.directory}/coverage.exec false sun.reflect.DelegatingClassLoader:MyClassLoader true true session true file localhost 9999 ${project.build.directory}/classdumps true ${jacoco.destFile} @project.groupId@ jacoco-maven-plugin prepare-agent report * java.* sun.* org.apache.maven.plugins maven-surefire-plugin ${coverageAgent} jacoco-0.8.11/jacoco-maven-plugin.test/it/it-customize-agent/src/000077500000000000000000000000001451257705100246155ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-customize-agent/src/main/000077500000000000000000000000001451257705100255415ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-customize-agent/src/main/java/000077500000000000000000000000001451257705100264625ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-customize-agent/src/main/java/Example.java000066400000000000000000000011641451257705100307220ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ public class Example { public void sayHello() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-customize-agent/src/test/000077500000000000000000000000001451257705100255745ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-customize-agent/src/test/java/000077500000000000000000000000001451257705100265155ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-customize-agent/src/test/java/ExampleTest.java000066400000000000000000000012121451257705100316070ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example().sayHello(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-customize-agent/verify.bsh000066400000000000000000000033511451257705100260320ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String agentOptions = "destfile=" + basedir + File.separator + "target" + File.separator + "coverage.exec" + ",append=false" + ",includes=*" + ",excludes=java.*:sun.*" + ",exclclassloader=sun.reflect.DelegatingClassLoader:MyClassLoader" + ",inclbootstrapclasses=true" + ",inclnolocationclasses=true" + ",sessionid=session" + ",dumponexit=true" + ",output=file" + ",address=localhost" + ",port=9999" + ",classdumpdir=" + basedir + File.separator + "target" + File.separator + "classdumps" + ",jmx=true"; //backslashes will be escaped agentOptions = agentOptions.replace("\\","\\\\"); String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( agentOptions ) < 0 ) { throw new RuntimeException( "Property was not configured, expected " + agentOptions ); } File file = new File( basedir, "target/coverage.exec" ); if ( !file.isFile() ) { throw new FileNotFoundException( "Could not find generated dump: " + file ); } File reportDir = new File( basedir, "target/site/jacoco" ); if ( !reportDir.isDirectory() ) { throw new RuntimeException( "Could not find generated report" ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-dump/000077500000000000000000000000001451257705100216555ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-dump/pom.xml000066400000000000000000000062301451257705100231730ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-dump @project.groupId@ jacoco-maven-plugin prepare-agent prepare-agent tcpserver dump integration-test dump check check BUNDLE CLASS COVEREDCOUNT 1 org.apache.maven.plugins maven-antrun-plugin 1.6 launch-server pre-integration-test run stop-server post-integration-test run jacoco-0.8.11/jacoco-maven-plugin.test/it/it-dump/src/000077500000000000000000000000001451257705100224445ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-dump/src/main/000077500000000000000000000000001451257705100233705ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-dump/src/main/java/000077500000000000000000000000001451257705100243115ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-dump/src/main/java/Server.java000066400000000000000000000020341451257705100264210ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ import java.io.File; /** * Simple server which runs as long a termination file is created. */ public class Server { public static void main(String[] args) throws Exception { System.out.println("Test server started"); // Wait for termination file to turn up // This option puts the target in a pseudo 'server' mode if (args.length == 1) { final File termFile = new File(args[0]); while (!termFile.exists()) { Thread.sleep(100); } } System.out.println("Test server stopped"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-dump/verify.bsh000066400000000000000000000015221451257705100236570ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( "All coverage checks have been met." ) < 0 ) { throw new RuntimeException( "Coverage checks were not met." ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/000077500000000000000000000000001451257705100243305ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/pom.xml000066400000000000000000000030411451257705100256430ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-includes-excludes @project.groupId@ jacoco-maven-plugin **/FileUtil* **/TestUtil* prepare-agent prepare-agent report report jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/src/000077500000000000000000000000001451257705100251175ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/src/main/000077500000000000000000000000001451257705100260435ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/src/main/java/000077500000000000000000000000001451257705100267645ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/src/main/java/org/000077500000000000000000000000001451257705100275535ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/src/main/java/org/project/000077500000000000000000000000001451257705100312215ustar00rootroot00000000000000DatabaseUtil.java000066400000000000000000000012261451257705100343500ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/src/main/java/org/project/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.project; public class DatabaseUtil { public void doStuff() { System.out.println("Do DatabaseUtil Stuff"); } } FileUtil.java000066400000000000000000000012161451257705100335220ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/src/main/java/org/project/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.project; public class FileUtil { public void doStuff() { System.out.println("Do FileUtil Stuff"); } } TestUtil.java000066400000000000000000000012161451257705100335620ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/src/main/java/org/project/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.project; public class TestUtil { public void doStuff() { System.out.println("Do TestUtil Stuff"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/src/test/000077500000000000000000000000001451257705100260765ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/src/test/java/000077500000000000000000000000001451257705100270175ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/src/test/java/org/000077500000000000000000000000001451257705100276065ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/src/test/java/org/project/000077500000000000000000000000001451257705100312545ustar00rootroot00000000000000TestDatabaseUtil.java000066400000000000000000000012561451257705100352460ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/src/test/java/org/project/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.project; import org.junit.Test; public class TestDatabaseUtil { @Test public void testDoStuff() { new DatabaseUtil().doStuff(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-includes-excludes/verify.bsh000066400000000000000000000024571451257705100263420ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String agentOptions = "excludes=**/FileUtil*:**/TestUtil*"; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( agentOptions ) < 0 ) { throw new RuntimeException("Include/Exclude was not configured correct" ); } File databaseUtilReportFile = new File( basedir, "target/site/jacoco/org.project/DatabaseUtil.html" ); if ( !databaseUtilReportFile.isFile() ) { throw new FileNotFoundException( "DatabaseUtil should NOT be excluded: " + databaseUtilReportFile ); } File testUtilReportFile = new File( basedir, "target/site/jacoco/org.project/TestUtil.html" ); if ( testUtilReportFile.isFile() ) { throw new RuntimeException( "TestUtil SHOULD be excluded: " + testUtilReportFile ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/000077500000000000000000000000001451257705100266035ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/invoker.properties000066400000000000000000000000341451257705100323730ustar00rootroot00000000000000invoker.java.version = 1.9+ jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/pom.xml000066400000000000000000000050531451257705100301230ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-java9-offline-instrumentation @project.groupId@ org.jacoco.agent runtime @project.version@ test org.apache.maven.plugins maven-compiler-plugin 9 9 @project.groupId@ jacoco-maven-plugin instrument-classes instrument restore-instrumented-classes restore-instrumented-classes report report ${project.build.directory}/coverage.exec org.apache.maven.plugins maven-surefire-plugin ${project.build.directory}/coverage.exec jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/src/000077500000000000000000000000001451257705100273725ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/src/main/000077500000000000000000000000001451257705100303165ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/src/main/java/000077500000000000000000000000001451257705100312375ustar00rootroot00000000000000module-info.java000066400000000000000000000010561451257705100342430ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/src/main/java/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ module org.example { } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/src/main/java/org/000077500000000000000000000000001451257705100320265ustar00rootroot00000000000000example/000077500000000000000000000000001451257705100334025ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/src/main/java/orgExample.java000066400000000000000000000012121451257705100356340ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/src/main/java/org/example/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.example; public class Example { public void sayHello() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/src/test/000077500000000000000000000000001451257705100303515ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/src/test/java/000077500000000000000000000000001451257705100312725ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/src/test/java/org/000077500000000000000000000000001451257705100320615ustar00rootroot00000000000000example/000077500000000000000000000000001451257705100334355ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/src/test/java/orgExampleTest.java000066400000000000000000000012401451257705100365300ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9-offline-instrumentation/src/test/java/org/example/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.example; import org.junit.Test; public class ExampleTest { @Test public void test() { new Example().sayHello(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9/000077500000000000000000000000001451257705100217225ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9/invoker.properties000066400000000000000000000000341451257705100255120ustar00rootroot00000000000000invoker.java.version = 1.9+ jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9/pom.xml000066400000000000000000000041061451257705100232400ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT ../setup-parent it-java9 org.apache.maven.plugins maven-compiler-plugin 9 9 @project.groupId@ jacoco-maven-plugin prepare-agent report check check INSTRUCTION COVEREDCOUNT 8 8 jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9/src/000077500000000000000000000000001451257705100225115ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9/src/main/000077500000000000000000000000001451257705100234355ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9/src/main/java/000077500000000000000000000000001451257705100243565ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9/src/main/java/Example.java000066400000000000000000000012501451257705100266120ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ public class Example { public void sayHello(String name) { // http://openjdk.java.net/jeps/280 System.out.println("Hello, " + name); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9/src/test/000077500000000000000000000000001451257705100234705ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9/src/test/java/000077500000000000000000000000001451257705100244115ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-java9/src/test/java/ExampleTest.java000066400000000000000000000012201451257705100275020ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example().sayHello("test"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/000077500000000000000000000000001451257705100233035ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-merge/000077500000000000000000000000001451257705100274055ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-merge/pom.xml000066400000000000000000000031431451257705100307230ustar00rootroot00000000000000 4.0.0 jacoco it-merge-passes 1.0-SNAPSHOT it-merge-passes-merge @project.groupId@ jacoco-maven-plugin merge merge ${project.parent.build.directory} *.exec jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project1/000077500000000000000000000000001451257705100300355ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project1/pom.xml000066400000000000000000000015421451257705100313540ustar00rootroot00000000000000 4.0.0 jacoco it-merge-passes 1.0-SNAPSHOT it-merge-passes-project1 jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project1/src/000077500000000000000000000000001451257705100306245ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project1/src/main/000077500000000000000000000000001451257705100315505ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project1/src/main/java/000077500000000000000000000000001451257705100324715ustar00rootroot00000000000000Example.java000066400000000000000000000011661451257705100346540ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project1/src/main/java/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Mads Mohr Christensen - implementation of MergeMojo * *******************************************************************************/ public class Example { public void sayHello() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project1/src/test/000077500000000000000000000000001451257705100316035ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project1/src/test/java/000077500000000000000000000000001451257705100325245ustar00rootroot00000000000000ExampleTest.java000066400000000000000000000012141451257705100355410ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project1/src/test/java/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Mads Mohr Christensen - implementation of MergeMojo * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example().sayHello(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project2/000077500000000000000000000000001451257705100300365ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project2/pom.xml000066400000000000000000000015421451257705100313550ustar00rootroot00000000000000 4.0.0 jacoco it-merge-passes 1.0-SNAPSHOT it-merge-passes-project2 jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project2/src/000077500000000000000000000000001451257705100306255ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project2/src/main/000077500000000000000000000000001451257705100315515ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project2/src/main/java/000077500000000000000000000000001451257705100324725ustar00rootroot00000000000000Example.java000066400000000000000000000011661451257705100346550ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project2/src/main/java/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Mads Mohr Christensen - implementation of MergeMojo * *******************************************************************************/ public class Example { public void sayHello() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project2/src/test/000077500000000000000000000000001451257705100316045ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project2/src/test/java/000077500000000000000000000000001451257705100325255ustar00rootroot00000000000000ExampleTest.java000066400000000000000000000012141451257705100355420ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/it-merge-passes-project2/src/test/java/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Mads Mohr Christensen - implementation of MergeMojo * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example().sayHello(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/pom.xml000066400000000000000000000034211451257705100246200ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-merge-passes pom it-merge-passes-project1 it-merge-passes-project2 it-merge-passes-merge @project.groupId@ jacoco-maven-plugin prepare-agent prepare-agent ${project.parent.build.directory}/${project.artifactId}.exec org.apache.maven.plugins maven-surefire-plugin ${argLine} jacoco-0.8.11/jacoco-maven-plugin.test/it/it-merge-passes/verify.bsh000066400000000000000000000016741451257705100253150ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Mads Mohr Christensen - implementation of MergeMojo * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( "Loading execution data file" ) < 0 ) { throw new RuntimeException( "Could not load execution data file" ); } if ( buildLog.indexOf( "Writing merged execution data to" ) < 0 ) { throw new RuntimeException( "Could not write merged execution data" ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/000077500000000000000000000000001451257705100233255ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/child-jar-without-sources/000077500000000000000000000000001451257705100303445ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/child-jar-without-sources/pom.xml000066400000000000000000000016101451257705100316570ustar00rootroot00000000000000 4.0.0 jacoco it-multi-module 1.0-SNAPSHOT child-jar-without-sources jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/child/000077500000000000000000000000001451257705100244105ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/child/pom.xml000066400000000000000000000015141451257705100257260ustar00rootroot00000000000000 4.0.0 jacoco it-multi-module 1.0-SNAPSHOT child jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/child/src/000077500000000000000000000000001451257705100251775ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/child/src/main/000077500000000000000000000000001451257705100261235ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/child/src/main/java/000077500000000000000000000000001451257705100270445ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/child/src/main/java/Example.java000066400000000000000000000011641451257705100313040ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ public class Example { public void sayHello() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/child/src/main/java/somepackage/000077500000000000000000000000001451257705100313235ustar00rootroot00000000000000Example.java000066400000000000000000000012121451257705100334760ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/child/src/main/java/somepackage/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package somepackage; public class Example { public void sayHello() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/child/src/test/000077500000000000000000000000001451257705100261565ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/child/src/test/java/000077500000000000000000000000001451257705100270775ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/child/src/test/java/ExampleTest.java000066400000000000000000000012121451257705100321710ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example().sayHello(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/pom.xml000066400000000000000000000033601451257705100246440ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-multi-module pom child child-jar-without-sources skip-child @project.groupId@ jacoco-maven-plugin prepare-agent prepare-agent report report org.apache.maven.plugins maven-surefire-plugin -ea ${argLine} jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/skip-child/000077500000000000000000000000001451257705100253545ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/skip-child/pom.xml000066400000000000000000000016251451257705100266750ustar00rootroot00000000000000 4.0.0 jacoco it-multi-module 1.0-SNAPSHOT skip-child true jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/skip-child/src/000077500000000000000000000000001451257705100261435ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/skip-child/src/test/000077500000000000000000000000001451257705100271225ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/skip-child/src/test/ExampleTest.java000066400000000000000000000011561451257705100322230ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multi-module/verify.bsh000066400000000000000000000036711451257705100253360ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( "Skipping JaCoCo execution due to missing classes directory." ) < 0 ) { throw new RuntimeException( "Execution should be skipped when target/classes does not exist." ); } File dump2 = new File( basedir, "skip-child/target/jacoco.exec" ); if ( dump2.isFile() ) { throw new RuntimeException( "Should not be executed for module 'skip-child', but dump found : " + dump2 ); } if ( !buildLog.contains( "argLine set to empty" ) ) { throw new RuntimeException( "Property not set to empty when skipping." ); } File file = new File( basedir, "child/target/jacoco.exec" ); if ( !file.isFile() ) { throw new FileNotFoundException( "Could not find generated dump: " + file ); } File xmlReport = new File( basedir, "child/target/site/jacoco/jacoco.xml" ); if ( !xmlReport.isFile() ) { throw new FileNotFoundException( "Could not find generated XML report: " + xmlReport ); } File csvReport = new File( basedir, "child/target/site/jacoco/jacoco.csv" ); if ( !csvReport.isFile() ) { throw new FileNotFoundException( "Could not find generated CSV report: " + csvReport ); } File htmlReport = new File( basedir, "child/target/site/jacoco/index.html" ); if ( !htmlReport.isFile() ) { throw new FileNotFoundException( "Could not find generated HTML report: " + htmlReport ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multiple-executions/000077500000000000000000000000001451257705100247275ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multiple-executions/pom.xml000066400000000000000000000041101451257705100262400ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-multiple-executions "-Da=\"1\"" -Db=2 @project.groupId@ jacoco-maven-plugin first prepare-agent ${project.build.directory}/nospace.exec second prepare-agent ${project.build.directory}/with space.exec "my" session third prepare-agent ${project.build.directory}/third.exec jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multiple-executions/src/000077500000000000000000000000001451257705100255165ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multiple-executions/src/main/000077500000000000000000000000001451257705100264425ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multiple-executions/src/main/java/000077500000000000000000000000001451257705100273635ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multiple-executions/src/main/java/Example.java000066400000000000000000000011641451257705100316230ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ public class Example { public void sayHello() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multiple-executions/src/test/000077500000000000000000000000001451257705100264755ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multiple-executions/src/test/java/000077500000000000000000000000001451257705100274165ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multiple-executions/src/test/java/ExampleTest.java000066400000000000000000000012121451257705100325100ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example().sayHello(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-multiple-executions/verify.bsh000066400000000000000000000024061451257705100267330ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; File file = new File( basedir, "target/nospace.exec" ); if ( file.isFile() ) { throw new FileNotFoundException( "Found unwanted dump: " + file ); } File file = new File( basedir, "target/with space.exec" ); if ( file.isFile() ) { throw new FileNotFoundException( "Found unwanted dump: " + file ); } file = new File( basedir, "target/third.exec" ); if ( !file.isFile() ) { throw new FileNotFoundException( "Could not find generated dump: " + file ); } String argLine = "\"-Da=\\\"1\\\"\" -Db=2"; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( argLine ) < 0 ) { throw new RuntimeException( "Original argLine was overwritten" ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/000077500000000000000000000000001451257705100255735ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child-without-main-classes/000077500000000000000000000000001451257705100327345ustar00rootroot00000000000000pom.xml000066400000000000000000000015551451257705100342000ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child-without-main-classes 4.0.0 jacoco it-offline-instrumentation 1.0-SNAPSHOT child-without-main-classes jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child-without-main-classes/src/000077500000000000000000000000001451257705100335235ustar00rootroot00000000000000test/000077500000000000000000000000001451257705100344235ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child-without-main-classes/srcjava/000077500000000000000000000000001451257705100353445ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child-without-main-classes/src/testExampleTest.java000066400000000000000000000011561451257705100404450ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child-without-main-classes/src/test/java/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child/000077500000000000000000000000001451257705100266565ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child/pom.xml000066400000000000000000000015301451257705100301720ustar00rootroot00000000000000 4.0.0 jacoco it-offline-instrumentation 1.0-SNAPSHOT child jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child/src/000077500000000000000000000000001451257705100274455ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child/src/main/000077500000000000000000000000001451257705100303715ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child/src/main/java/000077500000000000000000000000001451257705100313125ustar00rootroot00000000000000DoNotInstrument.java000066400000000000000000000011741451257705100352150ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child/src/main/java/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ public class DoNotInstrument { public void sayHello() { System.out.println("Hello world"); } } Example.java000066400000000000000000000011641451257705100334730ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child/src/main/java/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ public class Example { public void sayHello() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child/src/test/000077500000000000000000000000001451257705100304245ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child/src/test/java/000077500000000000000000000000001451257705100313455ustar00rootroot00000000000000ExampleTest.java000066400000000000000000000012121451257705100343600ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/child/src/test/java/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example().sayHello(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/pom.xml000066400000000000000000000051321451257705100271110ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-offline-instrumentation pom child child-without-main-classes @project.groupId@ org.jacoco.agent runtime @project.version@ test @project.groupId@ jacoco-maven-plugin instrument-classes instrument **/DoNotInstrument.class restore-instrumented-classes restore-instrumented-classes report report ${project.build.directory}/coverage.exec org.apache.maven.plugins maven-surefire-plugin ${project.build.directory}/coverage.exec jacoco-0.8.11/jacoco-maven-plugin.test/it/it-offline-instrumentation/verify.bsh000066400000000000000000000022121451257705100275720ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; File file = new File( basedir, "child/target/generated-classes/jacoco/Example.class" ); if ( !file.isFile() ) { throw new RuntimeException( "Could not find backup of instrumented class: " + file ); } file = new File( basedir, "child/target/generated-classes/jacoco/DoNotInstrument.class" ); if ( file.isFile() ) { throw new RuntimeException( "Excluded file should not be instrumented: " + file ); } file = new File( basedir, "child/target/coverage.exec" ); if ( !file.isFile() ) { throw new FileNotFoundException( "Could not find generated dump: " + file ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-prepend-property-skip/000077500000000000000000000000001451257705100251735ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-prepend-property-skip/pom.xml000066400000000000000000000025201451257705100265070ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-prepend-property-skip -Dfoo @project.groupId@ jacoco-maven-plugin prepare-agent true jacoco-0.8.11/jacoco-maven-plugin.test/it/it-prepend-property-skip/src/000077500000000000000000000000001451257705100257625ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-prepend-property-skip/src/test/000077500000000000000000000000001451257705100267415ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-prepend-property-skip/src/test/java/000077500000000000000000000000001451257705100276625ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-prepend-property-skip/src/test/java/ExampleTest.java000066400000000000000000000013111451257705100327540ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import org.junit.Test; import static org.junit.Assert.assertNotNull; public class ExampleTest { @Test public void test() { assertNotNull(System.getProperty("foo")); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-prepend-property/000077500000000000000000000000001451257705100242275ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-prepend-property/pom.xml000066400000000000000000000023601451257705100255450ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-prepend-property -ea @project.groupId@ jacoco-maven-plugin prepare-agent jacoco-0.8.11/jacoco-maven-plugin.test/it/it-prepend-property/verify.bsh000066400000000000000000000017241451257705100262350ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String agentOptions = "jacoco.exec -ea"; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( agentOptions ) < 0 ) { throw new RuntimeException( "Property was not configured" ); } File file = new File( basedir, "target/jacoco.exec" ); if ( !file.isFile() ) { throw new FileNotFoundException( "Could not find generated dump: " + file ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/000077500000000000000000000000001451257705100270555ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child1/000077500000000000000000000000001451257705100302215ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child1/pom.xml000066400000000000000000000017461451257705100315460ustar00rootroot00000000000000 4.0.0 jacoco it-report-aggregate-customization 1.0-SNAPSHOT child1 jar target/child1.coverage jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child1/src/000077500000000000000000000000001451257705100310105ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child1/src/main/000077500000000000000000000000001451257705100317345ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child1/src/main/java/000077500000000000000000000000001451257705100326555ustar00rootroot00000000000000package1/000077500000000000000000000000001451257705100342525ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child1/src/main/javaExample1.java000066400000000000000000000011471451257705100365740ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child1/src/main/java/package1/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ package package1; public class Example1 { public void a() { } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child1/src/test/000077500000000000000000000000001451257705100317675ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child1/src/test/java/000077500000000000000000000000001451257705100327105ustar00rootroot00000000000000package1/000077500000000000000000000000001451257705100343055ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child1/src/test/javaExample1Test.java000066400000000000000000000012431451257705100374640ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child1/src/test/java/package1/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ package package1; import org.junit.Test; public class Example1Test { @Test public void test() { new Example1().a(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child2/000077500000000000000000000000001451257705100302225ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child2/pom.xml000066400000000000000000000017461451257705100315470ustar00rootroot00000000000000 4.0.0 jacoco it-report-aggregate-customization 1.0-SNAPSHOT child2 jar target/child2.coverage jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child2/src/000077500000000000000000000000001451257705100310115ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child2/src/main/000077500000000000000000000000001451257705100317355ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child2/src/main/java/000077500000000000000000000000001451257705100326565ustar00rootroot00000000000000package2/000077500000000000000000000000001451257705100342545ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child2/src/main/javaExample2.java000066400000000000000000000011471451257705100365770ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child2/src/main/java/package2/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ package package2; public class Example2 { public void a() { } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child2/src/test/000077500000000000000000000000001451257705100317705ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child2/src/test/java/000077500000000000000000000000001451257705100327115ustar00rootroot00000000000000package2/000077500000000000000000000000001451257705100343075ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child2/src/test/javaExample2Test.java000066400000000000000000000012431451257705100374670ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/child2/src/test/java/package2/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ package package2; import org.junit.Test; public class Example2Test { @Test public void test() { new Example2().a(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/pom.xml000066400000000000000000000025731451257705100304010ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-report-aggregate-customization pom child1 child2 report @project.groupId@ jacoco-maven-plugin prepare-agent prepare-agent jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/report/000077500000000000000000000000001451257705100303705ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/report/pom.xml000066400000000000000000000042011451257705100317020ustar00rootroot00000000000000 4.0.0 jacoco it-report-aggregate-customization 1.0-SNAPSHOT report Aggregate Report ${project.groupId} child1 ${project.version} ${project.groupId} child2 ${project.version} @project.groupId@ jacoco-maven-plugin report-aggregate verify report-aggregate target/*.coverage target/child2.coverage target/jacoco-aggregate-customization true jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate-customization/verify.bsh000066400000000000000000000034761451257705100310710ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ import org.codehaus.plexus.util.*; import java.util.regex.*; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); // Test customization of dataFileIncludes and dataFileExcludes if ( !Pattern.compile( "Loading execution data file \\S*child1.target.child1.coverage").matcher( buildLog ).find() ) { throw new RuntimeException( "Execution data from child1 was not loaded." ); } if ( Pattern.compile( "Loading execution data file \\S*child2").matcher( buildLog ).find() ) { throw new RuntimeException( "Execution data from child2 was loaded." ); } // Test customization of outputDirectory File reportChild1 = new File( basedir, "report/target/jacoco-aggregate-customization/child1/index.html" ); if ( !reportChild1.isFile() ) { throw new RuntimeException( "Report for child1 was not created." ); } File reportChild2 = new File( basedir, "report/target/jacoco-aggregate-customization/child2/index.html" ); if ( !reportChild2.isFile() ) { throw new RuntimeException( "Report for child2 was not created." ); } // Test customization of includeCurrentProject File reportReport = new File( basedir, "report/target/jacoco-aggregate-customization/report/index.html" ); if ( !reportReport.isFile() ) { throw new RuntimeException( "Report for report was not created." ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/000077500000000000000000000000001451257705100241475ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1-test/000077500000000000000000000000001451257705100262705ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1-test/pom.xml000066400000000000000000000020701451257705100276040ustar00rootroot00000000000000 4.0.0 jacoco it-report-aggregate 1.0-SNAPSHOT child1-test jar jacoco child1 ${project.version} jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1-test/src/000077500000000000000000000000001451257705100270575ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1-test/src/test/000077500000000000000000000000001451257705100300365ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1-test/src/test/java/000077500000000000000000000000001451257705100307575ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1-test/src/test/java/package1/000077500000000000000000000000001451257705100324335ustar00rootroot00000000000000Example1bTest.java000066400000000000000000000012451451257705100356770ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1-test/src/test/java/package1/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ package package1; import org.junit.Test; public class Example1bTest { @Test public void test() { new Example1b().b(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1/000077500000000000000000000000001451257705100253135ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1/pom.xml000066400000000000000000000015721451257705100266350ustar00rootroot00000000000000 4.0.0 jacoco it-report-aggregate 1.0-SNAPSHOT child1 jar jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1/src/000077500000000000000000000000001451257705100261025ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1/src/main/000077500000000000000000000000001451257705100270265ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1/src/main/java/000077500000000000000000000000001451257705100277475ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1/src/main/java/package1/000077500000000000000000000000001451257705100314235ustar00rootroot00000000000000Example1a.java000066400000000000000000000011501451257705100340210ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1/src/main/java/package1/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ package package1; public class Example1a { public void a() { } } Example1b.java000066400000000000000000000011501451257705100340220ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1/src/main/java/package1/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ package package1; public class Example1b { public void b() { } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1/src/test/000077500000000000000000000000001451257705100270615ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1/src/test/java/000077500000000000000000000000001451257705100300025ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1/src/test/java/package1/000077500000000000000000000000001451257705100314565ustar00rootroot00000000000000Example1aTest.java000066400000000000000000000012451451257705100347210ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child1/src/test/java/package1/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ package package1; import org.junit.Test; public class Example1aTest { @Test public void test() { new Example1a().a(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2/000077500000000000000000000000001451257705100253145ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2/pom.xml000066400000000000000000000015721451257705100266360ustar00rootroot00000000000000 4.0.0 jacoco it-report-aggregate 1.0-SNAPSHOT child2 jar jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2/src/000077500000000000000000000000001451257705100261035ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2/src/main/000077500000000000000000000000001451257705100270275ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2/src/main/java/000077500000000000000000000000001451257705100277505ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2/src/main/java/package2/000077500000000000000000000000001451257705100314255ustar00rootroot00000000000000Example2.java000066400000000000000000000011471451257705100336710ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2/src/main/java/package2/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ package package2; public class Example2 { public void a() { } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2/src/test/000077500000000000000000000000001451257705100270625ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2/src/test/java/000077500000000000000000000000001451257705100300035ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2/src/test/java/package2/000077500000000000000000000000001451257705100314605ustar00rootroot00000000000000Example2Test.java000066400000000000000000000012431451257705100345610ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2/src/test/java/package2/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ package package2; import org.junit.Test; public class Example2Test { @Test public void test() { new Example2().a(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2v2/000077500000000000000000000000001451257705100255645ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2v2/pom.xml000066400000000000000000000015771451257705100271130ustar00rootroot00000000000000 4.0.0 jacoco it-report-aggregate 1.0-SNAPSHOT child2 2.0-SNAPSHOT jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2v2/src/000077500000000000000000000000001451257705100263535ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2v2/src/main/000077500000000000000000000000001451257705100272775ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2v2/src/main/java/000077500000000000000000000000001451257705100302205ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2v2/src/main/java/package2/000077500000000000000000000000001451257705100316755ustar00rootroot00000000000000Example2.java000066400000000000000000000011471451257705100341410ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2v2/src/main/java/package2/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ package package2; public class Example2 { public void a() { } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2v2/src/test/000077500000000000000000000000001451257705100273325ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2v2/src/test/java/000077500000000000000000000000001451257705100302535ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2v2/src/test/java/package2/000077500000000000000000000000001451257705100317305ustar00rootroot00000000000000Example2Test.java000066400000000000000000000012431451257705100350310ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/child2v2/src/test/java/package2/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ package package2; import org.junit.Test; public class Example2Test { @Test public void test() { new Example2().a(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/pom.xml000066400000000000000000000026541451257705100254730ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-report-aggregate pom child1 child1-test child2 child2v2 report @project.groupId@ jacoco-maven-plugin prepare-agent prepare-agent jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/report/000077500000000000000000000000001451257705100254625ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/report/pom.xml000066400000000000000000000035351451257705100270050ustar00rootroot00000000000000 4.0.0 jacoco it-report-aggregate 1.0-SNAPSHOT report Aggregate Report jacoco child1 ${project.version} compile jacoco child1-test ${project.version} test jacoco child2 [2-SNAPSHOT,) runtime @project.groupId@ jacoco-maven-plugin report-aggregate verify report-aggregate jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/report/src/000077500000000000000000000000001451257705100262515ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/report/src/test/000077500000000000000000000000001451257705100272305ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/report/src/test/java/000077500000000000000000000000001451257705100301515ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/report/src/test/java/packagereport/000077500000000000000000000000001451257705100330005ustar00rootroot00000000000000ReportTest.java000066400000000000000000000012051451257705100356750ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/report/src/test/java/packagereport/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package packagereport; import org.junit.Test; public class ReportTest { @Test public void test() { } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-aggregate/verify.bsh000066400000000000000000000046661451257705100261650ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ import org.codehaus.plexus.util.*; import java.util.regex.*; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( !Pattern.compile( "Loading execution data file \\S*child1.target.jacoco.exec").matcher( buildLog ).find() ) { throw new RuntimeException( "Execution data from child1 was not loaded." ); } if ( !Pattern.compile( "Loading execution data file \\S*child1-test.target.jacoco.exec").matcher( buildLog ).find() ) { throw new RuntimeException( "Execution data from child1-test was not loaded." ); } if ( !new File( basedir, "child2/target/jacoco.exec" ).isFile()) { throw new RuntimeException( "No execution data in child2." ); } if ( Pattern.compile( "Loading execution data file \\S*child2.target.jacoco.exec").matcher( buildLog ).find() ) { throw new RuntimeException( "Execution data from child2 was loaded, whereas range should exclude it." ); } if ( !Pattern.compile( "Loading execution data file \\S*child2v2.target.jacoco.exec").matcher( buildLog ).find() ) { throw new RuntimeException( "Execution data from child2v2 was not loaded." ); } if ( !Pattern.compile( "Loading execution data file \\S*report.target.jacoco.exec").matcher( buildLog ).find() ) { throw new RuntimeException( "Execution data from report was not loaded." ); } File reportChild1 = new File( basedir, "report/target/site/jacoco-aggregate/child1/index.html" ); if ( !reportChild1.isFile() ) { throw new RuntimeException( "Report for child1 was not created." ); } File reportChild1test = new File( basedir, "report/target/site/jacoco-aggregate/child1-test/index.html" ); if ( reportChild1test.isFile() ) { throw new RuntimeException( "Report for child1-test should not be created." ); } File reportChild2 = new File( basedir, "report/target/site/jacoco-aggregate/child2/index.html" ); if ( !reportChild2.isFile() ) { throw new RuntimeException( "Report for child2 was not created." ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-nomatch/000077500000000000000000000000001451257705100236525ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-nomatch/nomatch.exec000066400000000000000000000000301451257705100261420ustar00rootroot00000000000000ÀÀExamplejacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-nomatch/pom.xml000066400000000000000000000024611451257705100251720ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-report-nomatch @project.groupId@ jacoco-maven-plugin report report nomatch.exec jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-nomatch/src/000077500000000000000000000000001451257705100244415ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-nomatch/src/main/000077500000000000000000000000001451257705100253655ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-nomatch/src/main/java/000077500000000000000000000000001451257705100263065ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-nomatch/src/main/java/Example.java000066400000000000000000000010611451257705100305420ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ public class Example { } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-nomatch/verify.bsh000066400000000000000000000022151451257705100256540ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( "Classes in bundle " ) < 0 || buildLog.indexOf(" do not match with execution data." ) < 0 ) { throw new RuntimeException( "Warning 1 was not printed" ); } if ( buildLog.indexOf( "For report generation the same class files must be used as at runtime." ) < 0 ) { throw new RuntimeException( "Warning 2 was not printed" ); } if ( buildLog.indexOf( "Execution data for class Example does not match." ) < 0 ) { throw new RuntimeException( "Warning 3 was not printed" ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-select-formats/000077500000000000000000000000001451257705100251515ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-select-formats/pom.xml000066400000000000000000000030021451257705100264610ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-report-select-formats @project.groupId@ jacoco-maven-plugin prepare-agent report report XML CSV jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-select-formats/src/000077500000000000000000000000001451257705100257405ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-select-formats/src/main/000077500000000000000000000000001451257705100266645ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-select-formats/src/main/java/000077500000000000000000000000001451257705100276055ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-select-formats/src/main/java/Example.java000066400000000000000000000010611451257705100320410ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ public class Example { } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-select-formats/src/test/000077500000000000000000000000001451257705100267175ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-select-formats/src/test/java/000077500000000000000000000000001451257705100276405ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-select-formats/src/test/java/ExampleTest.java000066400000000000000000000011771451257705100327440ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-select-formats/verify.bsh000066400000000000000000000020771451257705100271610ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ import java.io.*; File htmlReportFile = new File( basedir, "target/site/jacoco/index.html" ); if ( htmlReportFile.isFile() ) { throw new RuntimeException( "Unexpected HTML report was created" ); } File xmlReportFile = new File( basedir, "target/site/jacoco/jacoco.xml" ); if ( !xmlReportFile.isFile() ) { throw new RuntimeException( "XML report was not created" ); } File csvReportFile = new File( basedir, "target/site/jacoco/jacoco.csv" ); if ( !csvReportFile.isFile() ) { throw new RuntimeException( "CSV report was not created" ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-unreadable-dump/000077500000000000000000000000001451257705100252665ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-unreadable-dump/data.txt000066400000000000000000000000151451257705100267340ustar00rootroot00000000000000Invalid data jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-unreadable-dump/invoker.properties000066400000000000000000000000361451257705100310600ustar00rootroot00000000000000invoker.buildResult = failure jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-unreadable-dump/pom.xml000066400000000000000000000024651451257705100266120ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-report-unreadable-dump @project.groupId@ jacoco-maven-plugin report report data.txt jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-unreadable-dump/src/000077500000000000000000000000001451257705100260555ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-unreadable-dump/src/main/000077500000000000000000000000001451257705100270015ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-unreadable-dump/src/main/resources/000077500000000000000000000000001451257705100310135ustar00rootroot00000000000000empty-file.txt000066400000000000000000000000001451257705100335360ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-unreadable-dump/src/main/resourcesjacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-unreadable-dump/verify.bsh000066400000000000000000000014241451257705100272710ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( "Invalid execution data file." ) < 0 ) { throw new RuntimeException( "Error was not printed" ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-without-debug/000077500000000000000000000000001451257705100250105ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-without-debug/pom.xml000066400000000000000000000031611451257705100263260ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-report-without-debug @project.groupId@ jacoco-maven-plugin prepare-agent prepare-agent report report org.apache.maven.plugins maven-compiler-plugin true none jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-without-debug/src/000077500000000000000000000000001451257705100255775ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-without-debug/src/main/000077500000000000000000000000001451257705100265235ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-without-debug/src/main/java/000077500000000000000000000000001451257705100274445ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-without-debug/src/main/java/Example.java000066400000000000000000000011641451257705100317040ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ public class Example { public void sayHello() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-without-debug/src/test/000077500000000000000000000000001451257705100265565ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-without-debug/src/test/java/000077500000000000000000000000001451257705100274775ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-without-debug/src/test/java/ExampleTest.java000066400000000000000000000012121451257705100325710ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example().sayHello(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-without-debug/verify.bsh000066400000000000000000000014331451257705100270130ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( "with debug information" ) < 0 ) { throw new RuntimeException( "No warning about debug information" ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-without-dump/000077500000000000000000000000001451257705100246675ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-without-dump/pom.xml000066400000000000000000000023151451257705100262050ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-report-without-dump @project.groupId@ jacoco-maven-plugin report report jacoco-0.8.11/jacoco-maven-plugin.test/it/it-report-without-dump/verify.bsh000066400000000000000000000014701451257705100266730ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String buildLog = FileUtils.fileRead( new File( basedir, "build.log" ) ); if ( buildLog.indexOf( "Skipping JaCoCo execution due to missing execution data file" ) < 0 ) { throw new RuntimeException( "Execution was not skipped" ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site-failsafe/000077500000000000000000000000001451257705100234245ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site-failsafe/invoker.properties000066400000000000000000000001731451257705100272200ustar00rootroot00000000000000invoker.goals = clean verify site # maven-site-plugin 3.3 works with at least Maven 2.2.1+ invoker.maven.version = 2.2.1+ jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site-failsafe/pom.xml000066400000000000000000000056331451257705100247500ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-site-failsafe org.apache.maven.plugins maven-failsafe-plugin 2.14.1 org.apache.maven.plugins maven-surefire-plugin 2.14.1 @project.groupId@ jacoco-maven-plugin default-prepare-agent prepare-agent default-prepare-agent-integration prepare-agent-integration default-report-integration report-integration org.apache.maven.plugins maven-failsafe-plugin default-integration-test integration-test org.apache.maven.plugins maven-site-plugin 3.3 true @project.groupId@ jacoco-maven-plugin @project.version@ jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site-failsafe/src/000077500000000000000000000000001451257705100242135ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site-failsafe/src/main/000077500000000000000000000000001451257705100251375ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site-failsafe/src/main/java/000077500000000000000000000000001451257705100260605ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site-failsafe/src/main/java/Example.java000066400000000000000000000012711451257705100303170ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ public class Example { public void sayHello() { System.out.println("Hello world"); } public void sayHelloIT() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site-failsafe/src/test/000077500000000000000000000000001451257705100251725ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site-failsafe/src/test/java/000077500000000000000000000000001451257705100261135ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site-failsafe/src/test/java/ExampleIT.java000066400000000000000000000012121451257705100306020ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import org.junit.Test; public class ExampleIT { @Test public void test() { new Example().sayHelloIT(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site-failsafe/src/test/java/ExampleTest.java000066400000000000000000000012121451257705100312050ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example().sayHello(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site-failsafe/verify.bsh000066400000000000000000000041451451257705100254320ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String projectReportsPage = FileUtils.fileRead( new File( basedir, "target/site/project-reports.html" ) ); if ( projectReportsPage.indexOf( "JaCoCo Coverage Report." ) < 0 ) { throw new RuntimeException( "project-reports.html does not contain link to JaCoCo report" ); } File htmlReportFile = new File( basedir, "target/site/jacoco/index.html" ); if ( !htmlReportFile.isFile() ) { throw new RuntimeException( "HTML report was not created" ); } File xmlReportFile = new File( basedir, "target/site/jacoco/jacoco.xml" ); if ( !xmlReportFile.isFile() ) { throw new RuntimeException( "XML report was not created" ); } File csvReportFile = new File( basedir, "target/site/jacoco/jacoco.csv" ); if ( !csvReportFile.isFile() ) { throw new RuntimeException( "CSV report was not created" ); } if ( projectReportsPage.indexOf( "JaCoCo IT Coverage Report." ) < 0 ) { throw new RuntimeException( "project-reports.html does not contain link to JaCoCo Integration report" ); } File htmlReportFile = new File( basedir, "target/site/jacoco-it/index.html" ); if ( !htmlReportFile.isFile() ) { throw new RuntimeException( "Integration HTML report was not created" ); } File xmlReportFile = new File( basedir, "target/site/jacoco-it/jacoco.xml" ); if ( !xmlReportFile.isFile() ) { throw new RuntimeException( "Integration XML report was not created" ); } File csvReportFile = new File( basedir, "target/site/jacoco-it/jacoco.csv" ); if ( !csvReportFile.isFile() ) { throw new RuntimeException( "Integration CSV report was not created" ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site/000077500000000000000000000000001451257705100216545ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site/invoker.properties000066400000000000000000000001661451257705100254520ustar00rootroot00000000000000invoker.goals = clean test site # maven-site-plugin 3.0 requires at least Maven 2.2.0 invoker.maven.version = 2.2.0+ jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site/pom.xml000066400000000000000000000031431451257705100231720ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT it-site @project.groupId@ jacoco-maven-plugin prepare-agent org.apache.maven.plugins maven-site-plugin 3.3 true @project.groupId@ jacoco-maven-plugin @project.version@ jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site/src/000077500000000000000000000000001451257705100224435ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site/src/main/000077500000000000000000000000001451257705100233675ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site/src/main/java/000077500000000000000000000000001451257705100243105ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site/src/main/java/Example.java000066400000000000000000000011641451257705100265500ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ public class Example { public void sayHello() { System.out.println("Hello world"); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site/src/test/000077500000000000000000000000001451257705100234225ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site/src/test/java/000077500000000000000000000000001451257705100243435ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site/src/test/java/ExampleTest.java000066400000000000000000000012121451257705100274350ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import org.junit.Test; public class ExampleTest { @Test public void test() { new Example().sayHello(); } } jacoco-0.8.11/jacoco-maven-plugin.test/it/it-site/verify.bsh000066400000000000000000000025601451257705100236610ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ import java.io.*; import org.codehaus.plexus.util.*; String projectReportsPage = FileUtils.fileRead( new File( basedir, "target/site/project-reports.html" ) ); if ( projectReportsPage.indexOf( "JaCoCo Coverage Report." ) < 0 ) { throw new RuntimeException( "project-reports.html does not contain link to JaCoCo report" ); } File htmlReportFile = new File( basedir, "target/site/jacoco/index.html" ); if ( !htmlReportFile.isFile() ) { throw new RuntimeException( "HTML report was not created" ); } File xmlReportFile = new File( basedir, "target/site/jacoco/jacoco.xml" ); if ( !xmlReportFile.isFile() ) { throw new RuntimeException( "XML report was not created" ); } File csvReportFile = new File( basedir, "target/site/jacoco/jacoco.csv" ); if ( !csvReportFile.isFile() ) { throw new RuntimeException( "CSV report was not created" ); } jacoco-0.8.11/jacoco-maven-plugin.test/it/settings.xml000066400000000000000000000023641451257705100226650ustar00rootroot00000000000000 it-repo true local.central @localRepositoryUrl@ true true local.central @localRepositoryUrl@ true true jacoco-0.8.11/jacoco-maven-plugin.test/it/setup-parent/000077500000000000000000000000001451257705100227255ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin.test/it/setup-parent/invoker.properties000066400000000000000000000001171451257705100265170ustar00rootroot00000000000000invoker.goals = org.jacoco:jacoco-maven-plugin:${project.version}:help install jacoco-0.8.11/jacoco-maven-plugin.test/it/setup-parent/pom.xml000066400000000000000000000034531451257705100242470ustar00rootroot00000000000000 4.0.0 jacoco setup-parent 1.0-SNAPSHOT pom junit junit @junit.version@ test @project.groupId@ jacoco-maven-plugin @project.version@ org.apache.maven.plugins maven-compiler-plugin 2.3.2 org.apache.maven.plugins maven-surefire-plugin 2.9 org.apache.maven.plugins maven-jar-plugin 2.3.1 jacoco-0.8.11/jacoco-maven-plugin.test/pom.xml000066400000000000000000000054471451257705100212110ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.tests 0.8.11 ../org.jacoco.tests jacoco-maven-plugin.test jar JaCoCo :: Test :: Maven Plugin invoker.mavenOpts org.jacoco.maven.* org.apache.maven.plugins maven-invoker-plugin ${skipTests} it ${project.build.directory}/it */pom.xml verify ${project.build.directory}/local-repo clean install it/settings.xml org.jacoco:org.jacoco.agent:${project.version}:jar:runtime 8 8 install run jacoco-0.8.11/jacoco-maven-plugin/000077500000000000000000000000001451257705100167045ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin/.classpath000066400000000000000000000014171451257705100206720ustar00rootroot00000000000000 jacoco-0.8.11/jacoco-maven-plugin/.project000066400000000000000000000013271451257705100203560ustar00rootroot00000000000000 jacoco-maven-plugin org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core/.settings jacoco-0.8.11/jacoco-maven-plugin/META-INF/000077500000000000000000000000001451257705100200445ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin/META-INF/m2e/000077500000000000000000000000001451257705100205275ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin/META-INF/m2e/lifecycle-mapping-metadata.xml000066400000000000000000000020071451257705100264160ustar00rootroot00000000000000 prepare-agent prepare-agent-integration merge report report-integration report-aggregate check dump instrument restore-instrumented-classes jacoco-0.8.11/jacoco-maven-plugin/pom.xml000066400000000000000000000102061451257705100202200ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.build 0.8.11 ../org.jacoco.build jacoco-maven-plugin maven-plugin https://www.jacoco.org/jacoco/trunk/doc/maven.html JaCoCo :: Maven Plugin The JaCoCo Maven Plugin provides the JaCoCo runtime agent to your tests and allows basic report creation. 3.0 8 8 8 org.apache.maven maven-plugin-api ${project.prerequisites.maven} provided org.apache.maven maven-core ${project.prerequisites.maven} provided org.codehaus.plexus plexus-utils 3.0.24 org.apache.maven.shared file-management 3.1.0 org.apache.maven.reporting maven-reporting-api ${project.prerequisites.maven} ${project.groupId} org.jacoco.agent runtime ${project.groupId} org.jacoco.core ${project.groupId} org.jacoco.report org.apache.maven.plugin-tools maven-plugin-annotations 3.4 provided src META-INF META-INF org.apache.maven.plugins maven-toolchains-plugin org.apache.maven.plugins maven-plugin-plugin default-descriptor process-classes help-goal helpmojo report package report jacoco-0.8.11/jacoco-maven-plugin/src/000077500000000000000000000000001451257705100174735ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin/src/org/000077500000000000000000000000001451257705100202625ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/000077500000000000000000000000001451257705100215205ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/000077500000000000000000000000001451257705100226265ustar00rootroot00000000000000jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/AbstractAgentMojo.java000066400000000000000000000205711451257705100270450ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.maven; import java.io.File; import java.util.List; import java.util.Map; import java.util.Properties; import org.apache.maven.artifact.Artifact; import org.apache.maven.plugins.annotations.Parameter; import org.codehaus.plexus.util.StringUtils; import org.jacoco.core.runtime.AgentOptions; /** * Base class for preparing a property pointing to the JaCoCo runtime agent that * can be passed as a VM argument to the application under test. */ public abstract class AbstractAgentMojo extends AbstractJacocoMojo { /** * Name of the JaCoCo Agent artifact. */ static final String AGENT_ARTIFACT_NAME = "org.jacoco:org.jacoco.agent"; /** * Name of the property used in maven-osgi-test-plugin. */ static final String TYCHO_ARG_LINE = "tycho.testArgLine"; /** * Name of the property used in maven-surefire-plugin. */ static final String SUREFIRE_ARG_LINE = "argLine"; /** * Map of plugin artifacts. */ @Parameter(property = "plugin.artifactMap", required = true, readonly = true) Map pluginArtifactMap; /** * Allows to specify property which will contains settings for JaCoCo Agent. * If not specified, then "argLine" would be used for "jar" packaging and * "tycho.testArgLine" for "eclipse-test-plugin". */ @Parameter(property = "jacoco.propertyName") String propertyName; /** * If set to true and the execution data file already exists, coverage data * is appended to the existing file. If set to false, an existing execution * data file will be replaced. */ @Parameter(property = "jacoco.append") Boolean append; /** * A list of class names to include in instrumentation. May use wildcard * characters (* and ?). When not specified everything will be included. */ @Parameter private List includes; /** * A list of class names to exclude from instrumentation. May use wildcard * characters (* and ?). When not specified nothing will be excluded. Except * for performance optimization or technical corner cases this option is * normally not required. If you want to exclude classes from the report * please configure the report goal accordingly. */ @Parameter private List excludes; /** * A list of class loader names, that should be excluded from execution * analysis. The list entries are separated by a colon (:) and may use * wildcard characters (* and ?). This option might be required in case of * special frameworks that conflict with JaCoCo code instrumentation, in * particular class loaders that do not have access to the Java runtime * classes. */ @Parameter(property = "jacoco.exclClassLoaders") String exclClassLoaders; /** * Specifies whether also classes from the bootstrap classloader should be * instrumented. Use this feature with caution, it needs heavy * includes/excludes tuning. */ @Parameter(property = "jacoco.inclBootstrapClasses") Boolean inclBootstrapClasses; /** * Specifies whether classes without source location should be instrumented. */ @Parameter(property = "jacoco.inclNoLocationClasses") Boolean inclNoLocationClasses; /** * A session identifier that is written with the execution data. Without * this parameter a random identifier is created by the agent. */ @Parameter(property = "jacoco.sessionId") String sessionId; /** * If set to true coverage data will be written on VM shutdown. */ @Parameter(property = "jacoco.dumpOnExit") Boolean dumpOnExit; /** * Output method to use for writing coverage data. Valid options are: *
    *
  • file: At VM termination execution data is written to a file.
  • *
  • tcpserver: The agent listens for incoming connections on the TCP port * specified by the {@link #address} and {@link #port}. Execution data is * written to this TCP connection.
  • *
  • tcpclient: At startup the agent connects to the TCP port specified by * the {@link #address} and {@link #port}. Execution data is written to this * TCP connection.
  • *
  • none: Do not produce any output.
  • *
*/ @Parameter(property = "jacoco.output") String output; /** * IP address or hostname to bind to when the output method is tcpserver or * connect to when the output method is tcpclient. In tcpserver mode the * value "*" causes the agent to accept connections on any local address. */ @Parameter(property = "jacoco.address") String address; /** * Port to bind to when the output method is tcpserver or connect to when * the output method is tcpclient. In tcpserver mode the port must be * available, which means that if multiple JaCoCo agents should run on the * same machine, different ports have to be specified. */ @Parameter(property = "jacoco.port") Integer port; /** * If a directory is specified for this parameter the JaCoCo agent dumps all * class files it processes to the given location. This can be useful for * debugging purposes or in case of dynamically created classes for example * when scripting engines are used. */ @Parameter(property = "jacoco.classDumpDir") File classDumpDir; /** * If set to true the agent exposes functionality via JMX. */ @Parameter(property = "jacoco.jmx") Boolean jmx; @Override public void executeMojo() { final String name = getEffectivePropertyName(); final Properties projectProperties = getProject().getProperties(); final String oldValue = projectProperties.getProperty(name); final String newValue = createAgentOptions() .prependVMArguments(oldValue, getAgentJarFile()); getLog().info(name + " set to " + newValue); projectProperties.setProperty(name, newValue); } @Override protected void skipMojo() { final String name = getEffectivePropertyName(); final Properties projectProperties = getProject().getProperties(); final String oldValue = projectProperties.getProperty(name); if (oldValue == null) { getLog().info(name + " set to empty"); projectProperties.setProperty(name, ""); } } File getAgentJarFile() { final Artifact jacocoAgentArtifact = pluginArtifactMap .get(AGENT_ARTIFACT_NAME); return jacocoAgentArtifact.getFile(); } AgentOptions createAgentOptions() { final AgentOptions agentOptions = new AgentOptions(); agentOptions.setDestfile(getDestFile().getAbsolutePath()); if (append != null) { agentOptions.setAppend(append.booleanValue()); } if (includes != null && !includes.isEmpty()) { agentOptions .setIncludes(StringUtils.join(includes.iterator(), ":")); } if (excludes != null && !excludes.isEmpty()) { agentOptions .setExcludes(StringUtils.join(excludes.iterator(), ":")); } if (exclClassLoaders != null) { agentOptions.setExclClassloader(exclClassLoaders); } if (inclBootstrapClasses != null) { agentOptions.setInclBootstrapClasses( inclBootstrapClasses.booleanValue()); } if (inclNoLocationClasses != null) { agentOptions.setInclNoLocationClasses( inclNoLocationClasses.booleanValue()); } if (sessionId != null) { agentOptions.setSessionId(sessionId); } if (dumpOnExit != null) { agentOptions.setDumpOnExit(dumpOnExit.booleanValue()); } if (output != null) { agentOptions.setOutput(output); } if (address != null) { agentOptions.setAddress(address); } if (port != null) { agentOptions.setPort(port.intValue()); } if (classDumpDir != null) { agentOptions.setClassDumpDir(classDumpDir.getAbsolutePath()); } if (jmx != null) { agentOptions.setJmx(jmx.booleanValue()); } return agentOptions; } String getEffectivePropertyName() { if (isPropertyNameSpecified()) { return propertyName; } if (isEclipseTestPluginPackaging()) { return TYCHO_ARG_LINE; } return SUREFIRE_ARG_LINE; } boolean isPropertyNameSpecified() { return propertyName != null && !"".equals(propertyName); } boolean isEclipseTestPluginPackaging() { return "eclipse-test-plugin".equals(getProject().getPackaging()); } /** * @return the destFile */ abstract File getDestFile(); } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/AbstractJacocoMojo.java000066400000000000000000000040531451257705100272020ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.maven; import org.apache.maven.plugin.AbstractMojo; import org.apache.maven.plugin.MojoExecutionException; import org.apache.maven.plugin.MojoFailureException; import org.apache.maven.plugins.annotations.Parameter; import org.apache.maven.project.MavenProject; /** * Base class for JaCoCo Mojos. */ public abstract class AbstractJacocoMojo extends AbstractMojo { /** * Maven project. */ @Parameter(property = "project", readonly = true) private MavenProject project; /** * Flag used to suppress execution. */ @Parameter(property = "jacoco.skip", defaultValue = "false") private boolean skip; public final void execute() throws MojoExecutionException, MojoFailureException { if (skip) { getLog().info( "Skipping JaCoCo execution because property jacoco.skip is set."); skipMojo(); return; } executeMojo(); } /** * Executes Mojo. * * @throws MojoExecutionException * if an unexpected problem occurs. Throwing this exception * causes a "BUILD ERROR" message to be displayed. * @throws MojoFailureException * if an expected problem (such as a compilation failure) * occurs. Throwing this exception causes a "BUILD FAILURE" * message to be displayed. */ protected abstract void executeMojo() throws MojoExecutionException, MojoFailureException; /** * Skips Mojo. */ protected void skipMojo() { } /** * @return Maven project */ protected final MavenProject getProject() { return project; } } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/AbstractReportMojo.java000066400000000000000000000133231451257705100272570ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * troosan - add support for format selection * *******************************************************************************/ package org.jacoco.maven; import java.io.File; import java.io.IOException; import java.util.List; import java.util.Locale; import org.apache.maven.doxia.sink.SinkFactory; import org.apache.maven.plugin.AbstractMojo; import org.apache.maven.plugin.MojoExecutionException; import org.apache.maven.plugins.annotations.Parameter; import org.apache.maven.project.MavenProject; import org.apache.maven.reporting.MavenMultiPageReport; import org.apache.maven.reporting.MavenReportException; import org.jacoco.report.IReportGroupVisitor; import org.jacoco.report.IReportVisitor; /** * Base class for creating a code coverage report for tests of a single project * in multiple formats (HTML, XML, and CSV). */ public abstract class AbstractReportMojo extends AbstractMojo implements MavenMultiPageReport { /** * Encoding of the generated reports. */ @Parameter(property = "project.reporting.outputEncoding", defaultValue = "UTF-8") String outputEncoding; /** * A list of report formats to generate. Supported formats are HTML, XML and * CSV. Defaults to all formats if no values are given. * * @since 0.8.7 */ @Parameter(defaultValue = "HTML,XML,CSV") List formats; /** * Name of the root node HTML report pages. * * @since 0.7.7 */ @Parameter(defaultValue = "${project.name}") String title; /** * Footer text used in HTML report pages. * * @since 0.7.7 */ @Parameter String footer; /** * Encoding of the source files. */ @Parameter(property = "project.build.sourceEncoding", defaultValue = "UTF-8") String sourceEncoding; /** * A list of class files to include in the report. May use wildcard * characters (* and ?). When not specified everything will be included. */ @Parameter List includes; /** * A list of class files to exclude from the report. May use wildcard * characters (* and ?). When not specified nothing will be excluded. */ @Parameter List excludes; /** * Flag used to suppress execution. */ @Parameter(property = "jacoco.skip", defaultValue = "false") boolean skip; /** * Maven project. */ @Parameter(property = "project", readonly = true) MavenProject project; public String getDescription(final Locale locale) { return getName(locale) + " Coverage Report."; } public boolean isExternalReport() { return true; } public String getCategoryName() { return CATEGORY_PROJECT_REPORTS; } /** * Returns the list of class files to include in the report. * * @return class files to include, may contain wildcard characters */ List getIncludes() { return includes; } /** * Returns the list of class files to exclude from the report. * * @return class files to exclude, may contain wildcard characters */ List getExcludes() { return excludes; } public boolean canGenerateReport() { if (skip) { getLog().info( "Skipping JaCoCo execution because property jacoco.skip is set."); return false; } if (!canGenerateReportRegardingDataFiles()) { getLog().info( "Skipping JaCoCo execution due to missing execution data file."); return false; } if (!canGenerateReportRegardingClassesDirectory()) { getLog().info( "Skipping JaCoCo execution due to missing classes directory."); return false; } return true; } abstract boolean canGenerateReportRegardingDataFiles(); abstract boolean canGenerateReportRegardingClassesDirectory(); abstract File getOutputDirectory(); public void generate( @SuppressWarnings("deprecation") final org.codehaus.doxia.sink.Sink sink, final Locale locale) throws MavenReportException { generate(sink, null, locale); } public void generate(final org.apache.maven.doxia.sink.Sink sink, final SinkFactory sinkFactory, final Locale locale) throws MavenReportException { if (!canGenerateReport()) { return; } executeReport(locale); } /** * This method is called when the report generation is invoked directly as a * standalone Mojo. */ public void execute() throws MojoExecutionException { if (!canGenerateReport()) { return; } try { executeReport(Locale.getDefault()); } catch (final MavenReportException e) { throw new MojoExecutionException("An error has occurred in " + getName(Locale.ENGLISH) + " report generation.", e); } } private void executeReport(final Locale locale) throws MavenReportException { try { final ReportSupport support = new ReportSupport(getLog()); loadExecutionData(support); addFormatters(support, locale); final IReportVisitor visitor = support.initRootVisitor(); createReport(visitor, support); visitor.visitEnd(); } catch (final IOException e) { throw new MavenReportException( "Error while creating report: " + e.getMessage(), e); } } private void addFormatters(final ReportSupport support, final Locale locale) throws IOException { getOutputDirectory().mkdirs(); for (final ReportFormat f : formats) { support.addVisitor(f.createVisitor(this, locale)); } } abstract void loadExecutionData(final ReportSupport support) throws IOException; abstract void createReport(final IReportGroupVisitor visitor, final ReportSupport support) throws IOException; } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/AgentITMojo.java000066400000000000000000000031131451257705100256070ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ package org.jacoco.maven; import java.io.File; import org.apache.maven.plugins.annotations.LifecyclePhase; import org.apache.maven.plugins.annotations.Mojo; import org.apache.maven.plugins.annotations.Parameter; import org.apache.maven.plugins.annotations.ResolutionScope; /** * Same as prepare-agent, but provides default values suitable for * integration-tests: *
    *
  • bound to pre-integration-test phase
  • *
  • different destFile
  • *
* * @since 0.6.4 */ @Mojo(name = "prepare-agent-integration", defaultPhase = LifecyclePhase.PRE_INTEGRATION_TEST, requiresDependencyResolution = ResolutionScope.RUNTIME, threadSafe = true) public class AgentITMojo extends AbstractAgentMojo { /** * Path to the output file for execution data. */ @Parameter(property = "jacoco.destFile", defaultValue = "${project.build.directory}/jacoco-it.exec") private File destFile; /** * @return the destFile */ @Override File getDestFile() { return destFile; } } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/AgentMojo.java000066400000000000000000000063631451257705100253640ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.maven; import java.io.File; import org.apache.maven.plugins.annotations.LifecyclePhase; import org.apache.maven.plugins.annotations.Mojo; import org.apache.maven.plugins.annotations.Parameter; import org.apache.maven.plugins.annotations.ResolutionScope; /** *

* Prepares a property pointing to the JaCoCo runtime agent that can be passed * as a VM argument to the application under test. Depending on the project * packaging type by default a property with the following name is set: *

* *
    *
  • tycho.testArgLine for packaging type eclipse-test-plugin and
  • *
  • argLine otherwise.
  • *
* *

* If your project already defines VM arguments for test execution, be sure that * they will include property defined by JaCoCo. *

* *

* One of the ways to do this in case of maven-surefire-plugin - is to use * syntax for late * property evaluation: *

* *
 *   <plugin>
 *     <groupId>org.apache.maven.plugins</groupId>
 *     <artifactId>maven-surefire-plugin</artifactId>
 *     <configuration>
 *       <argLine>@{argLine} -your -extra -arguments</argLine>
 *     </configuration>
 *   </plugin>
 * 
* *

* You can define empty property to avoid JVM startup error * Could not find or load main class @{argLine} when using late * property evaluation and jacoco-maven-plugin not executed. *

* *

* Another way is to define "argLine" as a Maven property rather than as part of * the configuration of maven-surefire-plugin: *

* *
 *   <properties>
 *     <argLine>-your -extra -arguments</argLine>
 *   </properties>
 *   ...
 *   <plugin>
 *     <groupId>org.apache.maven.plugins</groupId>
 *     <artifactId>maven-surefire-plugin</artifactId>
 *     <configuration>
 *       <!-- no argLine here -->
 *     </configuration>
 *   </plugin>
 * 
* *

* Resulting coverage information is collected during execution and by default * written to a file when the process terminates. *

* * @since 0.5.3 */ @Mojo(name = "prepare-agent", defaultPhase = LifecyclePhase.INITIALIZE, requiresDependencyResolution = ResolutionScope.RUNTIME, threadSafe = true) public class AgentMojo extends AbstractAgentMojo { /** * Path to the output file for execution data. */ @Parameter(property = "jacoco.destFile", defaultValue = "${project.build.directory}/jacoco.exec") private File destFile; /** * @return the destFile */ @Override File getDestFile() { return destFile; } } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/CheckMojo.java000066400000000000000000000137331451257705100253420ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * Marc Hoffmann - redesign using report APIs * *******************************************************************************/ package org.jacoco.maven; import java.io.File; import java.io.IOException; import java.util.ArrayList; import java.util.List; import org.apache.maven.plugin.MojoExecutionException; import org.apache.maven.plugins.annotations.LifecyclePhase; import org.apache.maven.plugins.annotations.Mojo; import org.apache.maven.plugins.annotations.Parameter; import org.jacoco.core.analysis.ICoverageNode; import org.jacoco.report.IReportVisitor; import org.jacoco.report.check.IViolationsOutput; import org.jacoco.report.check.Limit; import org.jacoco.report.check.Rule; /** * Checks that the code coverage metrics are being met. * * @since 0.6.1 */ @Mojo(name = "check", defaultPhase = LifecyclePhase.VERIFY, threadSafe = true) public class CheckMojo extends AbstractJacocoMojo implements IViolationsOutput { private static final String MSG_SKIPPING = "Skipping JaCoCo execution due to missing execution data file:"; private static final String CHECK_SUCCESS = "All coverage checks have been met."; private static final String CHECK_FAILED = "Coverage checks have not been met. See log for details."; /** *

* Check configuration used to specify rules on element types (BUNDLE, * PACKAGE, CLASS, SOURCEFILE or METHOD) with a list of limits. Each limit * applies to a certain counter (INSTRUCTION, LINE, BRANCH, COMPLEXITY, * METHOD, CLASS) and defines a minimum or maximum for the corresponding * value (TOTALCOUNT, COVEREDCOUNT, MISSEDCOUNT, COVEREDRATIO, MISSEDRATIO). * If a limit refers to a ratio it must be in the range from 0.0 to 1.0 * where the number of decimal places will also determine the precision in * error messages. A limit ratio may optionally be declared as a percentage * where 0.80 and 80% represent the same value. *

* *

* If not specified the following defaults are assumed: *

* *
    *
  • rule element: BUNDLE
  • *
  • limit counter: INSTRUCTION
  • *
  • limit value: COVEREDRATIO
  • *
* *

* This example requires an overall instruction coverage of 80% and no class * must be missed: *

* *
	 * {@code
	 * 
	 *   
	 *     BUNDLE
	 *     
	 *       
	 *         INSTRUCTION
	 *         COVEREDRATIO
	 *         0.80
	 *       
	 *       
	 *         CLASS
	 *         MISSEDCOUNT
	 *         0
	 *       
	 *     
	 *   
	 * }
	 * 
* *

* This example requires a line coverage minimum of 50% for every class * except test classes: *

* *
	 * {@code
	 * 
	 *   
	 *     CLASS
	 *     
	 *       *Test
	 *     
	 *     
	 *       
	 *         LINE
	 *         COVEREDRATIO
	 *         50%
	 *       
	 *     
	 *   
	 * }
	 * 
*/ @Parameter(required = true) private List rules; /** * Halt the build if any of the checks fail. */ @Parameter(property = "jacoco.haltOnFailure", defaultValue = "true", required = true) private boolean haltOnFailure; /** * File with execution data. */ @Parameter(defaultValue = "${project.build.directory}/jacoco.exec") private File dataFile; /** * A list of class files to include into analysis. May use wildcard * characters (* and ?). When not specified everything will be included. */ @Parameter private List includes; /** * A list of class files to exclude from analysis. May use wildcard * characters (* and ?). When not specified nothing will be excluded. */ @Parameter private List excludes; private boolean violations; private boolean canCheckCoverage() { if (!dataFile.exists()) { getLog().info(MSG_SKIPPING + dataFile); return false; } final File classesDirectory = new File( getProject().getBuild().getOutputDirectory()); if (!classesDirectory.exists()) { getLog().info( "Skipping JaCoCo execution due to missing classes directory:" + classesDirectory); return false; } return true; } @Override public void executeMojo() throws MojoExecutionException { if (!canCheckCoverage()) { return; } executeCheck(); } private void executeCheck() throws MojoExecutionException { violations = false; final ReportSupport support = new ReportSupport(getLog()); final List checkerrules = new ArrayList(); for (final RuleConfiguration r : rules) { checkerrules.add(r.rule); } support.addRulesChecker(checkerrules, this); try { final IReportVisitor visitor = support.initRootVisitor(); support.loadExecutionData(dataFile); support.processProject(visitor, getProject(), includes, excludes); visitor.visitEnd(); } catch (final IOException e) { throw new MojoExecutionException( "Error while checking code coverage: " + e.getMessage(), e); } if (violations) { if (this.haltOnFailure) { throw new MojoExecutionException(CHECK_FAILED); } else { this.getLog().warn(CHECK_FAILED); } } else { this.getLog().info(CHECK_SUCCESS); } } public void onViolation(final ICoverageNode node, final Rule rule, final Limit limit, final String message) { this.getLog().warn(message); violations = true; } } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/DumpMojo.java000066400000000000000000000072761451257705100252370ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Chas Honton, Marc R. Hoffmann - initial implementation * *******************************************************************************/ package org.jacoco.maven; import static java.lang.String.format; import java.io.File; import java.io.IOException; import java.net.InetAddress; import org.apache.maven.plugin.MojoExecutionException; import org.apache.maven.plugins.annotations.LifecyclePhase; import org.apache.maven.plugins.annotations.Mojo; import org.apache.maven.plugins.annotations.Parameter; import org.jacoco.core.tools.ExecDumpClient; import org.jacoco.core.tools.ExecFileLoader; /** *

* Request a dump over TCP/IP from a JaCoCo agent running in * tcpserver mode. *

* *

* Note concerning parallel builds: While the dump goal as such is thread safe, * it has to be considered that TCP/IP server ports of the agents are a shared * resource. *

* * @since 0.6.4 */ @Mojo(name = "dump", defaultPhase = LifecyclePhase.POST_INTEGRATION_TEST, threadSafe = true) public class DumpMojo extends AbstractJacocoMojo { /** * Path to the output file for execution data. */ @Parameter(property = "jacoco.destFile", defaultValue = "${project.build.directory}/jacoco.exec") private File destFile; /** * If set to true and the execution data file already exists, coverage data * is appended to the existing file. If set to false, an existing execution * data file will be replaced. */ @Parameter(property = "jacoco.append", defaultValue = "true") private boolean append; /** * Sets whether execution data should be downloaded from the remote host. */ @Parameter(property = "jacoco.dump", defaultValue = "true") private boolean dump; /** * Sets whether a reset command should be sent after the execution data has * been dumped. */ @Parameter(property = "jacoco.reset", defaultValue = "false") private boolean reset; /** * IP address or hostname to connect to. */ @Parameter(property = "jacoco.address") private String address; /** * Port number to connect to. If multiple JaCoCo agents should run on the * same machine, different ports have to be specified for the agents. */ @Parameter(property = "jacoco.port", defaultValue = "6300") private int port; /** * Number of retries which the goal will attempt to establish a connection. * This can be used to wait until the target JVM is successfully launched. */ @Parameter(property = "jacoco.retryCount", defaultValue = "10") private int retryCount; @Override public void executeMojo() throws MojoExecutionException { final ExecDumpClient client = new ExecDumpClient() { @Override protected void onConnecting(final InetAddress address, final int port) { getLog().info(format("Connecting to %s:%s", address, Integer.valueOf(port))); } @Override protected void onConnectionFailure(final IOException exception) { getLog().info(exception.getMessage()); } }; client.setDump(dump); client.setReset(reset); client.setRetryCount(retryCount); try { final ExecFileLoader loader = client.dump(address, port); if (dump) { getLog().info(format("Dumping execution data to %s", destFile.getAbsolutePath())); loader.save(destFile, append); } } catch (final IOException e) { throw new MojoExecutionException("Unable to dump coverage data", e); } } } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/FileFilter.java000066400000000000000000000051271451257705100255230ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ package org.jacoco.maven; import java.io.File; import java.io.IOException; import java.util.List; import org.codehaus.plexus.util.FileUtils; import org.codehaus.plexus.util.StringUtils; /** * A file filter using includes/excludes patterns. */ public class FileFilter { private static final String DEFAULT_INCLUDES = "**"; private static final String DEFAULT_EXCLUDES = ""; private final List includes; private final List excludes; /** * Construct a new FileFilter * * @param includes * list of includes patterns * @param excludes * list of excludes patterns */ public FileFilter(final List includes, final List excludes) { this.includes = includes; this.excludes = excludes; } /** * Returns a list of file names. * * @param directory * the directory to scan * @return a list of files * @throws IOException * if file system access fails */ public List getFileNames(final File directory) throws IOException { return FileUtils.getFileNames(directory, getIncludes(), getExcludes(), false); } /** * Returns a list of files. * * @param directory * the directory to scan * @return a list of files * @throws IOException * if file system access fails */ public List getFiles(final File directory) throws IOException { return FileUtils.getFiles(directory, getIncludes(), getExcludes()); } /** * Get the includes pattern * * @return the pattern */ public String getIncludes() { return this.buildPattern(this.includes, DEFAULT_INCLUDES); } /** * Get the excludes pattern * * @return the pattern */ public String getExcludes() { return this.buildPattern(this.excludes, DEFAULT_EXCLUDES); } private String buildPattern(final List patterns, final String defaultPattern) { String pattern = defaultPattern; if (patterns != null && !patterns.isEmpty()) { pattern = StringUtils.join(patterns.iterator(), ","); } return pattern; } } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/InstrumentMojo.java000066400000000000000000000077621451257705100265020ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.maven; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.util.List; import org.apache.maven.plugin.MojoExecutionException; import org.apache.maven.plugin.MojoFailureException; import org.apache.maven.plugins.annotations.LifecyclePhase; import org.apache.maven.plugins.annotations.Mojo; import org.apache.maven.plugins.annotations.Parameter; import org.codehaus.plexus.util.FileUtils; import org.codehaus.plexus.util.IOUtil; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.runtime.OfflineInstrumentationAccessGenerator; /** * Performs offline instrumentation. Note that after execution of test you must * restore original classes with help of "restore-instrumented-classes" goal. *

* Warning: The preferred way for code coverage analysis with * JaCoCo is on-the-fly instrumentation. Offline instrumentation has several * drawbacks and should only be used if a specific scenario explicitly requires * this mode. Please consult documentation about * offline instrumentation before using this mode. *

* * @since 0.6.2 */ @Mojo(name = "instrument", defaultPhase = LifecyclePhase.PROCESS_CLASSES, threadSafe = true) public class InstrumentMojo extends AbstractJacocoMojo { /** * A list of class files to include in instrumentation. May use wildcard * characters (* and ?). When not specified everything will be included. */ @Parameter private List includes; /** * A list of class files to exclude from instrumentation. May use wildcard * characters (* and ?). When not specified nothing will be excluded. Except * for performance optimization or technical corner cases this option is * normally not required. If you want to exclude classes from the report * please configure the report goal accordingly. */ @Parameter private List excludes; @Override public void executeMojo() throws MojoExecutionException, MojoFailureException { final File originalClassesDir = new File( getProject().getBuild().getDirectory(), "generated-classes/jacoco"); originalClassesDir.mkdirs(); final File classesDir = new File( getProject().getBuild().getOutputDirectory()); if (!classesDir.exists()) { getLog().info( "Skipping JaCoCo execution due to missing classes directory:" + classesDir); return; } final List fileNames; try { fileNames = new FileFilter(includes, excludes) .getFileNames(classesDir); } catch (final IOException e1) { throw new MojoExecutionException( "Unable to get list of files to instrument.", e1); } final Instrumenter instrumenter = new Instrumenter( new OfflineInstrumentationAccessGenerator()); for (final String fileName : fileNames) { if (fileName.endsWith(".class")) { final File source = new File(classesDir, fileName); final File backup = new File(originalClassesDir, fileName); InputStream input = null; OutputStream output = null; try { FileUtils.copyFile(source, backup); input = new FileInputStream(backup); output = new FileOutputStream(source); instrumenter.instrument(input, output, source.getPath()); } catch (final IOException e2) { throw new MojoExecutionException( "Unable to instrument file.", e2); } finally { IOUtil.close(input); IOUtil.close(output); } } } } } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/MergeMojo.java000066400000000000000000000072021451257705100253560ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Mads Mohr Christensen - implementation of MergeMojo * *******************************************************************************/ package org.jacoco.maven; import java.io.File; import java.io.IOException; import java.util.List; import org.apache.maven.plugin.MojoExecutionException; import org.apache.maven.plugin.MojoFailureException; import org.apache.maven.plugins.annotations.LifecyclePhase; import org.apache.maven.plugins.annotations.Mojo; import org.apache.maven.plugins.annotations.Parameter; import org.apache.maven.shared.model.fileset.FileSet; import org.apache.maven.shared.model.fileset.util.FileSetManager; import org.jacoco.core.tools.ExecFileLoader; /** * Mojo for merging a set of execution data files (*.exec) into a single file * * @since 0.6.4 */ @Mojo(name = "merge", defaultPhase = LifecyclePhase.GENERATE_RESOURCES, threadSafe = true) public class MergeMojo extends AbstractJacocoMojo { private static final String MSG_SKIPPING = "Skipping JaCoCo merge execution due to missing execution data files"; /** * Path to the output file for execution data. */ @Parameter(property = "jacoco.destFile", defaultValue = "${project.build.directory}/jacoco.exec") private File destFile; /** * This mojo accepts any number of execution data file sets. * *
	 * 
	 * <fileSets>
	 *   <fileSet>
	 *     <directory>${project.build.directory}</directory>
	 *     <includes>
	 *       <include>*.exec</include>
	 *     </includes>
	 *   </fileSet>
	 * </fileSets>
	 * 
	 * 
*/ @Parameter(required = true) private List fileSets; @Override protected void executeMojo() throws MojoExecutionException, MojoFailureException { if (!canMergeReports()) { return; } executeMerge(); } private boolean canMergeReports() { if (fileSets == null || fileSets.isEmpty()) { getLog().info(MSG_SKIPPING); return false; } return true; } private void executeMerge() throws MojoExecutionException { final ExecFileLoader loader = new ExecFileLoader(); load(loader); save(loader); } private void load(final ExecFileLoader loader) throws MojoExecutionException { final FileSetManager fileSetManager = new FileSetManager(); for (final FileSet fileSet : fileSets) { for (final String includedFilename : fileSetManager .getIncludedFiles(fileSet)) { final File inputFile = new File(fileSet.getDirectory(), includedFilename); if (inputFile.isDirectory()) { continue; } try { getLog().info("Loading execution data file " + inputFile.getAbsolutePath()); loader.load(inputFile); } catch (final IOException e) { throw new MojoExecutionException( "Unable to read " + inputFile.getAbsolutePath(), e); } } } } private void save(final ExecFileLoader loader) throws MojoExecutionException { if (loader.getExecutionDataStore().getContents().isEmpty()) { getLog().info(MSG_SKIPPING); return; } getLog().info("Writing merged execution data to " + destFile.getAbsolutePath()); try { loader.save(destFile, false); } catch (final IOException e) { throw new MojoExecutionException( "Unable to write merged file " + destFile.getAbsolutePath(), e); } } } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/ReportAggregateMojo.java000066400000000000000000000165271451257705100274130ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * John Oliver, Marc R. Hoffmann, Jan Wloka - initial API and implementation * *******************************************************************************/ package org.jacoco.maven; import java.io.File; import java.io.IOException; import java.util.ArrayList; import java.util.Arrays; import java.util.List; import java.util.Locale; import org.apache.maven.artifact.Artifact; import org.apache.maven.artifact.versioning.DefaultArtifactVersion; import org.apache.maven.artifact.versioning.InvalidVersionSpecificationException; import org.apache.maven.artifact.versioning.VersionRange; import org.apache.maven.model.Dependency; import org.apache.maven.plugins.annotations.Mojo; import org.apache.maven.plugins.annotations.Parameter; import org.apache.maven.project.MavenProject; import org.jacoco.report.IReportGroupVisitor; /** *

* Creates a structured code coverage report (HTML, XML, and CSV) from multiple * projects within reactor. The report is created from all modules this project * depends on, and optionally this project itself. From those projects class and * source files as well as JaCoCo execution data files will be collected. In * addition execution data is collected from the project itself. This also * allows to create coverage reports when tests are in separate projects than * the code under test, for example in case of integration tests. *

* *

* Using the dependency scope allows to distinguish projects which contribute * execution data but should not become part of the report: *

* *
    *
  • compile, runtime, provided: * Project source and execution data is included in the report.
  • *
  • test: Only execution data is considered for the report.
  • *
* * @since 0.7.7 */ @Mojo(name = "report-aggregate", threadSafe = true) public class ReportAggregateMojo extends AbstractReportMojo { /** * A list of execution data files to include in the report from each * project. May use wildcard characters (* and ?). When not specified all * *.exec files from the target folder will be included. */ @Parameter List dataFileIncludes; /** * A list of execution data files to exclude from the report. May use * wildcard characters (* and ?). When not specified nothing will be * excluded. */ @Parameter List dataFileExcludes; /** * Output directory for the reports. Note that this parameter is only * relevant if the goal is run from the command line or from the default * build lifecycle. If the goal is run indirectly as part of a site * generation, the output directory configured in the Maven Site Plugin is * used instead. */ @Parameter(defaultValue = "${project.reporting.outputDirectory}/jacoco-aggregate") private File outputDirectory; /** * Include this project in the report. If true then this projects class and * source files as well as JaCoCo execution data files will be collected. * * @since 0.8.9 */ @Parameter(defaultValue = "false") private boolean includeCurrentProject; /** * The projects in the reactor. */ @Parameter(property = "reactorProjects", readonly = true) private List reactorProjects; @Override boolean canGenerateReportRegardingDataFiles() { return true; } @Override boolean canGenerateReportRegardingClassesDirectory() { return true; } @Override void loadExecutionData(final ReportSupport support) throws IOException { // https://issues.apache.org/jira/browse/MNG-5440 if (dataFileIncludes == null) { dataFileIncludes = Arrays.asList("target/*.exec"); } final FileFilter filter = new FileFilter(dataFileIncludes, dataFileExcludes); loadExecutionData(support, filter, project.getBasedir()); for (final MavenProject dependency : findDependencies( Artifact.SCOPE_COMPILE, Artifact.SCOPE_RUNTIME, Artifact.SCOPE_PROVIDED, Artifact.SCOPE_TEST)) { loadExecutionData(support, filter, dependency.getBasedir()); } } private void loadExecutionData(final ReportSupport support, final FileFilter filter, final File basedir) throws IOException { for (final File execFile : filter.getFiles(basedir)) { support.loadExecutionData(execFile); } } @Override File getOutputDirectory() { return outputDirectory; } @Override void createReport(final IReportGroupVisitor visitor, final ReportSupport support) throws IOException { final IReportGroupVisitor group = visitor.visitGroup(title); if (includeCurrentProject) { processProject(support, group, project); } for (final MavenProject dependency : findDependencies( Artifact.SCOPE_COMPILE, Artifact.SCOPE_RUNTIME, Artifact.SCOPE_PROVIDED)) { processProject(support, group, dependency); } } private void processProject(final ReportSupport support, final IReportGroupVisitor group, final MavenProject project) throws IOException { support.processProject(group, project.getArtifactId(), project, getIncludes(), getExcludes(), sourceEncoding); } public File getReportOutputDirectory() { return outputDirectory; } public void setReportOutputDirectory(final File reportOutputDirectory) { if (reportOutputDirectory != null && !reportOutputDirectory .getAbsolutePath().endsWith("jacoco-aggregate")) { outputDirectory = new File(reportOutputDirectory, "jacoco-aggregate"); } else { outputDirectory = reportOutputDirectory; } } public String getOutputName() { return "jacoco-aggregate/index"; } public String getName(final Locale locale) { return "JaCoCo Aggregate"; } private List findDependencies(final String... scopes) { final List result = new ArrayList(); final List scopeList = Arrays.asList(scopes); for (final Object dependencyObject : project.getDependencies()) { final Dependency dependency = (Dependency) dependencyObject; if (scopeList.contains(dependency.getScope())) { final MavenProject project = findProjectFromReactor(dependency); if (project != null) { result.add(project); } } } return result; } /** * Note that if dependency specified using version range and reactor * contains multiple modules with same artifactId and groupId but of * different versions, then first dependency which matches range will be * selected. For example in case of range [0,2] if version 1 is * before version 2 in reactor, then version 1 will be selected. */ private MavenProject findProjectFromReactor(final Dependency d) { final VersionRange depVersionAsRange; try { depVersionAsRange = VersionRange .createFromVersionSpec(d.getVersion()); } catch (final InvalidVersionSpecificationException e) { throw new AssertionError(e); } for (final MavenProject p : reactorProjects) { final DefaultArtifactVersion pv = new DefaultArtifactVersion( p.getVersion()); if (p.getGroupId().equals(d.getGroupId()) && p.getArtifactId().equals(d.getArtifactId()) && depVersionAsRange.containsVersion(pv)) { return p; } } return null; } } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/ReportFormat.java000066400000000000000000000044671451257705100261300ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.maven; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.util.Locale; import org.jacoco.report.FileMultiReportOutput; import org.jacoco.report.IReportVisitor; import org.jacoco.report.csv.CSVFormatter; import org.jacoco.report.html.HTMLFormatter; import org.jacoco.report.xml.XMLFormatter; /** * Configurable output formats for the report goals. */ public enum ReportFormat { /** * Multi-page html report. */ HTML() { @Override IReportVisitor createVisitor(final AbstractReportMojo mojo, final Locale locale) throws IOException { final HTMLFormatter htmlFormatter = new HTMLFormatter(); htmlFormatter.setOutputEncoding(mojo.outputEncoding); htmlFormatter.setLocale(locale); if (mojo.footer != null) { htmlFormatter.setFooterText(mojo.footer); } return htmlFormatter.createVisitor( new FileMultiReportOutput(mojo.getOutputDirectory())); } }, /** * Single-file XML report. */ XML() { @Override IReportVisitor createVisitor(final AbstractReportMojo mojo, final Locale locale) throws IOException { final XMLFormatter xml = new XMLFormatter(); xml.setOutputEncoding(mojo.outputEncoding); return xml.createVisitor(new FileOutputStream( new File(mojo.getOutputDirectory(), "jacoco.xml"))); } }, /** * Single-file CSV report. */ CSV() { @Override IReportVisitor createVisitor(final AbstractReportMojo mojo, final Locale locale) throws IOException { final CSVFormatter csv = new CSVFormatter(); csv.setOutputEncoding(mojo.outputEncoding); return csv.createVisitor(new FileOutputStream( new File(mojo.getOutputDirectory(), "jacoco.csv"))); } }; abstract IReportVisitor createVisitor(AbstractReportMojo mojo, final Locale locale) throws IOException; } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/ReportITMojo.java000066400000000000000000000057241451257705100260360ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ package org.jacoco.maven; import java.io.File; import java.io.IOException; import java.util.Locale; import org.apache.maven.plugins.annotations.LifecyclePhase; import org.apache.maven.plugins.annotations.Mojo; import org.apache.maven.plugins.annotations.Parameter; import org.jacoco.report.IReportGroupVisitor; /** * Same as report, but provides default values suitable for * integration-tests: *
    *
  • bound to report-integration phase
  • *
  • different dataFile
  • *
* * @since 0.6.4 */ @Mojo(name = "report-integration", defaultPhase = LifecyclePhase.VERIFY, threadSafe = true) public class ReportITMojo extends AbstractReportMojo { /** * Output directory for the reports. Note that this parameter is only * relevant if the goal is run from the command line or from the default * build lifecycle. If the goal is run indirectly as part of a site * generation, the output directory configured in the Maven Site Plugin is * used instead. */ @Parameter(defaultValue = "${project.reporting.outputDirectory}/jacoco-it") private File outputDirectory; /** * File with execution data. */ @Parameter(defaultValue = "${project.build.directory}/jacoco-it.exec") private File dataFile; @Override boolean canGenerateReportRegardingDataFiles() { return dataFile.exists(); } @Override boolean canGenerateReportRegardingClassesDirectory() { return new File(project.getBuild().getOutputDirectory()).exists(); } @Override void loadExecutionData(final ReportSupport support) throws IOException { support.loadExecutionData(dataFile); } @Override File getOutputDirectory() { return outputDirectory; } @Override void createReport(final IReportGroupVisitor visitor, final ReportSupport support) throws IOException { support.processProject(visitor, title, project, getIncludes(), getExcludes(), sourceEncoding); } public File getReportOutputDirectory() { return outputDirectory; } public void setReportOutputDirectory(final File reportOutputDirectory) { if (reportOutputDirectory != null && !reportOutputDirectory .getAbsolutePath().endsWith("jacoco-it")) { outputDirectory = new File(reportOutputDirectory, "jacoco-it"); } else { outputDirectory = reportOutputDirectory; } } public String getOutputName() { return "jacoco-it/index"; } public String getName(final Locale locale) { return "JaCoCo IT"; } } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/ReportMojo.java000066400000000000000000000054701451257705100255770ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.maven; import java.io.File; import java.io.IOException; import java.util.Locale; import org.apache.maven.plugins.annotations.LifecyclePhase; import org.apache.maven.plugins.annotations.Mojo; import org.apache.maven.plugins.annotations.Parameter; import org.jacoco.report.IReportGroupVisitor; /** * Creates a code coverage report for tests of a single project in multiple * formats (HTML, XML, and CSV). * * @since 0.5.3 */ @Mojo(name = "report", defaultPhase = LifecyclePhase.VERIFY, threadSafe = true) public class ReportMojo extends AbstractReportMojo { /** * Output directory for the reports. Note that this parameter is only * relevant if the goal is run from the command line or from the default * build lifecycle. If the goal is run indirectly as part of a site * generation, the output directory configured in the Maven Site Plugin is * used instead. */ @Parameter(defaultValue = "${project.reporting.outputDirectory}/jacoco") private File outputDirectory; /** * File with execution data. */ @Parameter(property = "jacoco.dataFile", defaultValue = "${project.build.directory}/jacoco.exec") private File dataFile; @Override boolean canGenerateReportRegardingDataFiles() { return dataFile.exists(); } @Override boolean canGenerateReportRegardingClassesDirectory() { return new File(project.getBuild().getOutputDirectory()).exists(); } @Override void loadExecutionData(final ReportSupport support) throws IOException { support.loadExecutionData(dataFile); } @Override File getOutputDirectory() { return outputDirectory; } @Override void createReport(final IReportGroupVisitor visitor, final ReportSupport support) throws IOException { support.processProject(visitor, title, project, getIncludes(), getExcludes(), sourceEncoding); } public File getReportOutputDirectory() { return outputDirectory; } public void setReportOutputDirectory(final File reportOutputDirectory) { if (reportOutputDirectory != null && !reportOutputDirectory .getAbsolutePath().endsWith("jacoco")) { outputDirectory = new File(reportOutputDirectory, "jacoco"); } else { outputDirectory = reportOutputDirectory; } } public String getOutputName() { return "jacoco/index"; } public String getName(final Locale locale) { return "JaCoCo"; } } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/ReportSupport.java000066400000000000000000000200371451257705100263430ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * *******************************************************************************/ package org.jacoco.maven; import static java.lang.String.format; import java.io.File; import java.io.FileInputStream; import java.io.IOException; import java.io.InputStreamReader; import java.io.Reader; import java.util.ArrayList; import java.util.Collection; import java.util.List; import org.apache.maven.plugin.logging.Log; import org.apache.maven.project.MavenProject; import org.jacoco.core.analysis.Analyzer; import org.jacoco.core.analysis.CoverageBuilder; import org.jacoco.core.analysis.IBundleCoverage; import org.jacoco.core.analysis.IClassCoverage; import org.jacoco.core.tools.ExecFileLoader; import org.jacoco.report.IReportGroupVisitor; import org.jacoco.report.IReportVisitor; import org.jacoco.report.ISourceFileLocator; import org.jacoco.report.MultiReportVisitor; import org.jacoco.report.check.IViolationsOutput; import org.jacoco.report.check.Rule; import org.jacoco.report.check.RulesChecker; /** * Encapsulates the tasks to create reports for Maven projects. Instances are * supposed to be used in the following sequence: * *
    *
  1. Create an instance
  2. *
  3. Load one or multiple exec files with * loadExecutionData()
  4. *
  5. Add one or multiple formatters with addXXX() methods
  6. *
  7. Create the root visitor with initRootVisitor()
  8. *
  9. Process one or multiple projects with processProject()
  10. *
*/ final class ReportSupport { private final Log log; private final ExecFileLoader loader; private final List formatters; /** * Construct a new instance with the given log output. * * @param log * for log output */ public ReportSupport(final Log log) { this.log = log; this.loader = new ExecFileLoader(); this.formatters = new ArrayList(); } /** * Loads the given execution data file. * * @param execFile * execution data file to load * @throws IOException * if the file can't be loaded */ public void loadExecutionData(final File execFile) throws IOException { log.info("Loading execution data file " + execFile); loader.load(execFile); } public void addVisitor(final IReportVisitor visitor) { formatters.add(visitor); } public void addRulesChecker(final List rules, final IViolationsOutput output) { final RulesChecker checker = new RulesChecker(); checker.setRules(rules); formatters.add(checker.createVisitor(output)); } public IReportVisitor initRootVisitor() throws IOException { final IReportVisitor visitor = new MultiReportVisitor(formatters); visitor.visitInfo(loader.getSessionInfoStore().getInfos(), loader.getExecutionDataStore().getContents()); return visitor; } /** * Calculates coverage for the given project and emits it to the report * group without source references * * @param visitor * group visitor to emit the project's coverage to * @param project * the MavenProject * @param includes * list of includes patterns * @param excludes * list of excludes patterns * @throws IOException * if class files can't be read */ public void processProject(final IReportGroupVisitor visitor, final MavenProject project, final List includes, final List excludes) throws IOException { processProject(visitor, project.getArtifactId(), project, includes, excludes, new NoSourceLocator()); } /** * Calculates coverage for the given project and emits it to the report * group including source references * * @param visitor * group visitor to emit the project's coverage to * @param bundleName * name for this project in the report * @param project * the MavenProject * @param includes * list of includes patterns * @param excludes * list of excludes patterns * @param srcEncoding * encoding of the source files within this project * @throws IOException * if class files can't be read */ public void processProject(final IReportGroupVisitor visitor, final String bundleName, final MavenProject project, final List includes, final List excludes, final String srcEncoding) throws IOException { processProject(visitor, bundleName, project, includes, excludes, new SourceFileCollection(project, srcEncoding)); } private void processProject(final IReportGroupVisitor visitor, final String bundleName, final MavenProject project, final List includes, final List excludes, final ISourceFileLocator locator) throws IOException { final CoverageBuilder builder = new CoverageBuilder(); final File classesDir = new File( project.getBuild().getOutputDirectory()); if (classesDir.isDirectory()) { final Analyzer analyzer = new Analyzer( loader.getExecutionDataStore(), builder); final FileFilter filter = new FileFilter(includes, excludes); for (final File file : filter.getFiles(classesDir)) { analyzer.analyzeAll(file); } } final IBundleCoverage bundle = builder.getBundle(bundleName); logBundleInfo(bundle, builder.getNoMatchClasses()); visitor.visitBundle(bundle, locator); } private void logBundleInfo(final IBundleCoverage bundle, final Collection nomatch) { log.info(format("Analyzed bundle '%s' with %s classes", bundle.getName(), Integer.valueOf(bundle.getClassCounter().getTotalCount()))); if (!nomatch.isEmpty()) { log.warn(format( "Classes in bundle '%s' do not match with execution data. " + "For report generation the same class files must be used as at runtime.", bundle.getName())); for (final IClassCoverage c : nomatch) { log.warn(format("Execution data for class %s does not match.", c.getName())); } } if (bundle.containsCode() && bundle.getLineCounter().getTotalCount() == 0) { log.warn( "To enable source code annotation class files have to be compiled with debug information."); } } private class NoSourceLocator implements ISourceFileLocator { public Reader getSourceFile(final String packageName, final String fileName) { return null; } public int getTabWidth() { return 0; } } private class SourceFileCollection implements ISourceFileLocator { private final List sourceRoots; private final String encoding; public SourceFileCollection(final MavenProject project, final String encoding) { this.sourceRoots = getCompileSourceRoots(project); this.encoding = encoding; } public Reader getSourceFile(final String packageName, final String fileName) throws IOException { final String r; if (packageName.length() > 0) { r = packageName + '/' + fileName; } else { r = fileName; } for (final File sourceRoot : sourceRoots) { final File file = new File(sourceRoot, r); if (file.exists() && file.isFile()) { return new InputStreamReader(new FileInputStream(file), encoding); } } return null; } public int getTabWidth() { return 4; } } private static List getCompileSourceRoots( final MavenProject project) { final List result = new ArrayList(); for (final Object path : project.getCompileSourceRoots()) { result.add(resolvePath(project, (String) path)); } return result; } private static File resolvePath(final MavenProject project, final String path) { File file = new File(path); if (!file.isAbsolute()) { file = new File(project.getBasedir(), path); } return file; } } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/RestoreMojo.java000066400000000000000000000031441451257705100257430ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.maven; import java.io.File; import java.io.IOException; import org.apache.maven.plugin.MojoExecutionException; import org.apache.maven.plugin.MojoFailureException; import org.apache.maven.plugins.annotations.LifecyclePhase; import org.apache.maven.plugins.annotations.Mojo; import org.codehaus.plexus.util.FileUtils; /** * Restores original classes as they were before offline instrumentation. * * @since 0.6.2 */ @Mojo(name = "restore-instrumented-classes", defaultPhase = LifecyclePhase.PREPARE_PACKAGE, threadSafe = true) public class RestoreMojo extends AbstractJacocoMojo { @Override protected void executeMojo() throws MojoExecutionException, MojoFailureException { final File originalClassesDir = new File( getProject().getBuild().getDirectory(), "generated-classes/jacoco"); final File classesDir = new File( getProject().getBuild().getOutputDirectory()); try { FileUtils.copyDirectoryStructure(originalClassesDir, classesDir); } catch (final IOException e) { throw new MojoFailureException("Unable to restore classes.", e); } } } jacoco-0.8.11/jacoco-maven-plugin/src/org/jacoco/maven/RuleConfiguration.java000066400000000000000000000035751451257705100271420ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Kyle Lieber - implementation of CheckMojo * Marc Hoffmann - redesign using report APIs * *******************************************************************************/ package org.jacoco.maven; import java.util.List; import org.codehaus.plexus.util.StringUtils; import org.jacoco.core.analysis.ICoverageNode.ElementType; import org.jacoco.report.check.Limit; import org.jacoco.report.check.Rule; /** * Wrapper for {@link Rule} objects to allow Maven style includes/excludes lists * */ public class RuleConfiguration { final Rule rule; /** * Create a new configuration instance. */ public RuleConfiguration() { rule = new Rule(); } /** * @param element * element type this rule applies to TODO: use ElementType * directly once Maven 3 is required. */ public void setElement(final String element) { rule.setElement(ElementType.valueOf(element)); } /** * @param includes * includes patterns */ public void setIncludes(final List includes) { rule.setIncludes(StringUtils.join(includes.iterator(), ":")); } /** * * @param excludes * excludes patterns */ public void setExcludes(final List excludes) { rule.setExcludes(StringUtils.join(excludes.iterator(), ":")); } /** * @param limits * list of {@link Limit}s configured for this rule */ public void setLimits(final List limits) { rule.setLimits(limits); } } jacoco-0.8.11/jacoco/000077500000000000000000000000001451257705100143045ustar00rootroot00000000000000jacoco-0.8.11/jacoco/.project000066400000000000000000000005611451257705100157550ustar00rootroot00000000000000 jacoco org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature jacoco-0.8.11/jacoco/assembly.xml000066400000000000000000000101451451257705100166460ustar00rootroot00000000000000 distribution zip false ${basedir}/../org.jacoco.doc/docroot / true **/*.html ${basedir}/../org.jacoco.doc/target/generated-resources/xml/xslt /doc false *.html ${basedir}/../org.jacoco.doc/docroot / **/*.html ${basedir}/../org.jacoco.doc/target/site/jacoco-aggregate /coverage ${basedir}/../org.jacoco.doc/target/junit /test ${basedir}/../org.jacoco.report/src/org/jacoco/report/xml/report.dtd /coverage lib jacocoant.jar false ${project.groupId}:org.jacoco.ant:jar:nodeps lib jacococli.jar false ${project.groupId}:org.jacoco.cli:jar:nodeps lib jacocoagent.jar false ${project.groupId}:org.jacoco.agent:*:runtime lib ${artifact.artifactId}-${qualified.bundle.version}.${artifact.extension} false ${project.groupId}:org.jacoco.core ${project.groupId}:org.jacoco.report ${project.groupId}:org.jacoco.agent ${project.groupId}:org.jacoco.ant ${project.groupId}:org.jacoco.agent:*:runtime ${project.groupId}:org.jacoco.ant:*:nodeps /doc true false ${project.groupId}:org.jacoco.examples:zip /doc/api true false META-INF/ ${project.groupId}:org.jacoco.doc:*:javadoc jacoco-0.8.11/jacoco/pom.xml000066400000000000000000000077431451257705100156340ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.build 0.8.11 ../org.jacoco.build jacoco pom JaCoCo :: Distribution JaCoCo Standalone Distribution ${project.groupId} org.jacoco.core ${project.groupId} org.jacoco.report ${project.groupId} org.jacoco.agent ${project.groupId} org.jacoco.agent ${project.version} runtime ${project.groupId} org.jacoco.ant ${project.groupId} org.jacoco.ant nodeps ${project.groupId} org.jacoco.cli ${project.version} nodeps ${project.groupId} org.jacoco.examples ${project.version} zip ${project.groupId} org.jacoco.doc ${project.version} javadoc src org.apache.maven.plugins maven-assembly-plugin package single jacoco-${qualified.bundle.version} false assembly.xml org.apache.maven.plugins maven-enforcer-plugin enforce-distribution-size enforce verify 4600000 4000000 ${project.build.directory}/jacoco-${qualified.bundle.version}.zip jacoco-0.8.11/org.jacoco.agent.rt.test/000077500000000000000000000000001451257705100175715ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/.classpath000066400000000000000000000014151451257705100215550ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.agent.rt.test/.project000066400000000000000000000013771451257705100212500ustar00rootroot00000000000000 org.jacoco.agent.rt.test org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.agent.rt.test/pom.xml000066400000000000000000000026371451257705100211160ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.tests 0.8.11 ../org.jacoco.tests org.jacoco.agent.rt.test JaCoCo :: Test :: Agent RT org.jacoco.agent.rt.* ${project.groupId} org.jacoco.agent.rt ${project.groupId} org.jacoco.core.test junit junit jacoco-0.8.11/org.jacoco.agent.rt.test/src/000077500000000000000000000000001451257705100203605ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/000077500000000000000000000000001451257705100211475ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/000077500000000000000000000000001451257705100224055ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/000077500000000000000000000000001451257705100235035ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/000077500000000000000000000000001451257705100241305ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/000077500000000000000000000000001451257705100257445ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/AgentModuleTest.java000066400000000000000000000043141451257705100316550ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNotSame; import static org.junit.Assert.assertSame; import org.jacoco.core.test.validation.JavaVersion; import org.junit.Test; /** * Unit tests for {@link AgentModule}. */ public class AgentModuleTest { @Test public void isSupported_should_return_false_before_Java9() { Boolean expected = Boolean .valueOf(!JavaVersion.current().isBefore("9")); Boolean supported = Boolean.valueOf(AgentModule.isSupported()); assertEquals(expected, supported); } @Test public void should_only_load_classes_in_scope() throws Exception { AgentModule am = new AgentModule(); Class targetclass = am .loadClassInModule(TargetImpl.class); Target t = targetclass.getDeclaredConstructor().newInstance(); assertNotSame(this.getClass().getClassLoader(), t.getClass().getClassLoader()); assertSame(AgentModule.class.getProtectionDomain(), t.getClass().getProtectionDomain()); assertSame(t.getClass().getClassLoader(), t.getInnerClassInstance().getClass().getClassLoader()); assertNotSame(this.getClass().getClassLoader(), t.getInnerClassInstance().getClass().getClassLoader()); assertSame(this.getClass().getClassLoader(), t.getOtherClassInstance().getClass().getClassLoader()); } public interface Target { Object getInnerClassInstance(); Object getOtherClassInstance(); } public static class TargetImpl implements Target { static class Inner { } public Object getInnerClassInstance() { return new Inner(); } public Object getOtherClassInstance() { return new Other(); } } public static class Other { } } jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/AgentTest.java000066400000000000000000000222061451257705100305070ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertSame; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.io.ByteArrayInputStream; import java.lang.management.ManagementFactory; import javax.management.InstanceNotFoundException; import javax.management.MBeanServer; import javax.management.ObjectName; import org.jacoco.agent.rt.internal.output.FileOutput; import org.jacoco.agent.rt.internal.output.IAgentOutput; import org.jacoco.agent.rt.internal.output.NoneOutput; import org.jacoco.agent.rt.internal.output.TcpClientOutput; import org.jacoco.agent.rt.internal.output.TcpServerOutput; import org.jacoco.core.JaCoCo; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.AgentOptions.OutputMode; import org.jacoco.core.runtime.RuntimeData; import org.jacoco.core.tools.ExecFileLoader; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link Agent}. */ public class AgentTest implements IExceptionLogger, IAgentOutput { private AgentOptions options; private Boolean writeExecutionDataReset; private Exception loggedException; @Before public void setup() { options = new AgentOptions(); options.setOutput(OutputMode.file); // avoid network access (DNS lookup for id generation): options.setSessionId("test"); } @Test public void createController_should_create_defined_controller_type() { Agent agent = new Agent(options, this); options.setOutput(OutputMode.file); assertEquals(FileOutput.class, agent.createAgentOutput().getClass()); options.setOutput(OutputMode.tcpserver); assertEquals(TcpServerOutput.class, agent.createAgentOutput().getClass()); options.setOutput(OutputMode.tcpclient); assertEquals(TcpClientOutput.class, agent.createAgentOutput().getClass()); options.setOutput(OutputMode.none); assertEquals(NoneOutput.class, agent.createAgentOutput().getClass()); } @Test public void startup_should_set_defined_session_id() throws Exception { Agent agent = createAgent(); agent.startup(); assertEquals("test", agent.getData().getSessionId()); assertNull(loggedException); } @Test public void startup_should_create_random_session_id_when_undefined() throws Exception { options.setSessionId(null); Agent agent = createAgent(); agent.startup(); final String id1 = agent.getData().getSessionId(); agent = createAgent(); agent.startup(); final String id2 = agent.getData().getSessionId(); assertFalse(id1.equals(id2)); assertNull(loggedException); } @Test public void startup_should_log_and_rethrow_exception() throws Exception { final Exception expected = new Exception(); Agent agent = new Agent(options, this) { @Override IAgentOutput createAgentOutput() { return new IAgentOutput() { public void startup(AgentOptions options, RuntimeData data) throws Exception { throw expected; } public void shutdown() { } public void writeExecutionData(boolean reset) { } }; } }; try { agent.startup(); fail("Exception expected"); } catch (Exception actual) { assertSame(expected, actual); assertSame(expected, loggedException); } } @Test public void startup_should_register_mbean_when_enabled() throws Exception { options.setJmx(true); Agent agent = createAgent(); agent.startup(); ObjectName objectName = new ObjectName("org.jacoco:type=Runtime"); final MBeanServer server = ManagementFactory.getPlatformMBeanServer(); assertEquals(JaCoCo.VERSION, server.getAttribute(objectName, "Version")); // cleanup as MBean is registered globally agent.shutdown(); } @Test public void startup_should_not_register_mbean_when_disabled() throws Exception { Agent agent = createAgent(); agent.startup(); ObjectName objectName = new ObjectName("org.jacoco:type=Runtime"); try { ManagementFactory.getPlatformMBeanServer().getMBeanInfo(objectName); fail("InstanceNotFoundException expected"); } catch (InstanceNotFoundException e) { } } @Test public void shutdown_should_write_execution_data_when_enabled() throws Exception { Agent agent = createAgent(); agent.startup(); agent.shutdown(); assertEquals(Boolean.FALSE, writeExecutionDataReset); assertNull(loggedException); } @Test public void shutdown_should_not_write_execution_data_when_disabled() throws Exception { options.setDumpOnExit(false); Agent agent = createAgent(); agent.startup(); agent.shutdown(); assertNull(writeExecutionDataReset); assertNull(loggedException); } @Test public void shutdown_should_log_exception() throws Exception { final Exception expected = new Exception(); Agent agent = new Agent(options, this) { @Override IAgentOutput createAgentOutput() { return new IAgentOutput() { public void startup(AgentOptions options, RuntimeData data) { } public void shutdown() throws Exception { throw expected; } public void writeExecutionData(boolean reset) { } }; } }; agent.startup(); agent.shutdown(); assertSame(expected, loggedException); } @Test public void shutdown_should_deregister_mbean_when_enabled() throws Exception { options.setJmx(true); Agent agent = createAgent(); agent.startup(); agent.shutdown(); ObjectName objectName = new ObjectName("org.jacoco:type=Runtime"); try { ManagementFactory.getPlatformMBeanServer().getMBeanInfo(objectName); fail("InstanceNotFoundException expected"); } catch (InstanceNotFoundException e) { } } @Test public void getVersion_should_return_current_version() { Agent agent = createAgent(); assertEquals(JaCoCo.VERSION, agent.getVersion()); } @Test public void getSessionId_should_return_session_id() throws Exception { Agent agent = createAgent(); agent.startup(); assertEquals("test", agent.getSessionId()); } @Test public void setSessionId_should_modify_session_id() throws Exception { Agent agent = createAgent(); agent.startup(); agent.setSessionId("new_id"); assertEquals("new_id", agent.getSessionId()); } @Test public void reset_should_reset_probes() { Agent agent = createAgent(); boolean[] probes = agent.getData() .getExecutionData(Long.valueOf(0x12345678), "Foo", 1) .getProbes(); probes[0] = true; agent.reset(); assertFalse(probes[0]); } @Test public void getExecutionData_should_return_probes_and_session_id() throws Exception { Agent agent = createAgent(); agent.startup(); agent.getData().getExecutionData(Long.valueOf(0x12345678), "Foo", 1) .getProbes()[0] = true; byte[] data = agent.getExecutionData(true); ExecFileLoader loader = new ExecFileLoader(); loader.load(new ByteArrayInputStream(data)); assertEquals("Foo", loader.getExecutionDataStore().get(0x12345678).getName()); assertEquals("test", loader.getSessionInfoStore().getInfos().get(0).getId()); } @Test public void getExecutionData_should_reset_probes_when_enabled() throws Exception { Agent agent = createAgent(); agent.startup(); final boolean[] probes = agent.getData() .getExecutionData(Long.valueOf(0x12345678), "Foo", 1) .getProbes(); probes[0] = true; agent.getExecutionData(true); assertFalse(probes[0]); } @Test public void getExecutionData_should_not_reset_probes_when_disabled() throws Exception { Agent agent = createAgent(); agent.startup(); final boolean[] probes = agent.getData() .getExecutionData(Long.valueOf(0x12345678), "Foo", 1) .getProbes(); probes[0] = true; agent.getExecutionData(false); assertTrue(probes[0]); } @Test public void dump_should_trigger_writeExecutionData_with_reset() throws Exception { Agent agent = createAgent(); agent.startup(); agent.dump(true); assertEquals(Boolean.TRUE, writeExecutionDataReset); assertNull(loggedException); } @Test public void dump_should_trigger_writeExecutionData_without_reset() throws Exception { Agent agent = createAgent(); agent.startup(); agent.dump(false); assertEquals(Boolean.FALSE, writeExecutionDataReset); assertNull(loggedException); } private Agent createAgent() { return new Agent(options, this) { @Override IAgentOutput createAgentOutput() { return AgentTest.this; } }; } // === IExceptionLogger === public void logExeption(Exception ex) { loggedException = ex; } // === IAgentOutput === public void startup(AgentOptions options, RuntimeData data) { } public void shutdown() { } public void writeExecutionData(boolean reset) { writeExecutionDataReset = Boolean.valueOf(reset); } } jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/ClassFileDumperTest.java000066400000000000000000000044441451257705100324770ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; import static org.junit.Assert.assertArrayEquals; import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileInputStream; import java.io.IOException; import java.io.InputStream; import org.junit.Before; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TemporaryFolder; /** * Unit tests for {@link ClassFileDumper}. */ public class ClassFileDumperTest { @Rule public TemporaryFolder folder = new TemporaryFolder(); private byte[] contents; @Before public void setup() throws IOException { contents = "just some bytes".getBytes("UTF-8"); } @Test public void testDumpClassWithPackage() throws IOException { final File location = new File(folder.getRoot(), "classes"); final ClassFileDumper dumper = new ClassFileDumper(location.toString()); dumper.dump("org/jacoco/examples/Foo$Inner", contents); assertContents(location, "org/jacoco/examples/Foo$Inner.aff06045a340cd62.class"); } @Test public void testDumpClassInDefaultPackage() throws IOException { final File location = new File(folder.getRoot(), "classes"); final ClassFileDumper dumper = new ClassFileDumper(location.toString()); dumper.dump("Main", contents); assertContents(location, "Main.aff06045a340cd62.class"); } @Test public void testNoDumps() throws IOException { final ClassFileDumper dumper = new ClassFileDumper(null); dumper.dump("Main", contents); } private void assertContents(File location, String filename) throws IOException { InputStream in = new FileInputStream(new File(location, filename)); ByteArrayOutputStream buffer = new ByteArrayOutputStream(); int b; while ((b = in.read()) != -1) { buffer.write(b); } in.close(); assertArrayEquals(contents, buffer.toByteArray()); } } jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/ConfigLoaderTest.java000066400000000000000000000044671451257705100320160ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; import java.util.Properties; import org.junit.Test; /** * Unit tests for {@link ConfigLoader}. */ public class ConfigLoaderTest { @Test public void testResource() { Properties system = new Properties(); Properties config = ConfigLoader.load( "/org/jacoco/agent/rt/internal/agent-test.properties", system); assertEquals("tcpclient", config.get("output")); } @Test public void testNoResource() { Properties system = new Properties(); Properties config = ConfigLoader.load("does-not-exist.properties", system); assertTrue(config.isEmpty()); } @Test public void testSystemProperties() { Properties system = new Properties(); system.setProperty("jacoco-agent.output", "mbean"); system.setProperty("output", "tcpserver"); // no prefix system.setProperty("jacoco-agent.sessionid", "testid"); Properties config = ConfigLoader.load( "/org/jacoco/agent/rt/internal/agent-test.properties", system); assertEquals("mbean", config.get("output")); assertEquals("3333", config.get("port")); assertEquals("testid", config.get("sessionid")); } @Test public void testSubstituteProperties() { Properties system = new Properties(); system.setProperty("user.home", "/home/jacoco"); system.setProperty("java.version", "1.5.0"); Properties config = ConfigLoader.load( "/org/jacoco/agent/rt/internal/agent-subst-test.properties", system); assertEquals("no$replace}", config.get("key0")); assertEquals("/home/jacoco/coverage/jacoco-1.5.0.exec", config.get("key1")); assertEquals("$/home/jacoco", config.get("key2")); assertEquals("/home/jacoco}}", config.get("key3")); assertEquals("${does.not.exist}", config.get("key4")); } } jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/CoverageTransformerTest.java000066400000000000000000000201651451257705100334310ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.InputStream; import java.lang.instrument.IllegalClassFormatException; import java.security.CodeSource; import java.security.ProtectionDomain; import java.security.cert.Certificate; import org.jacoco.core.JaCoCo; import org.jacoco.core.runtime.AbstractRuntime; import org.jacoco.core.runtime.AgentOptions; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.MethodVisitor; /** * Unit tests for {@link CoverageTransformer}. */ public class CoverageTransformerTest { private ExceptionRecorder recorder; private AgentOptions options; private ClassLoader classLoader; private ProtectionDomain protectionDomain; private StubRuntime runtime; @Before public void setup() { recorder = new ExceptionRecorder(); options = new AgentOptions(); classLoader = getClass().getClassLoader(); protectionDomain = getClass().getProtectionDomain(); runtime = new StubRuntime(); } @After public void teardown() { recorder.assertNoException(); } @Test public void testFilterAgentClass() { CoverageTransformer t = createTransformer(); assertFalse(t.filter(classLoader, "org/jacoco/agent/rt/internal/somepkg/SomeClass", protectionDomain)); } @Test public void testFilterInclBootstrapClassesPositive() { options.setInclBootstrapClasses(true); CoverageTransformer t = createTransformer(); assertTrue(t.filter(null, "java/util/TreeSet", protectionDomain)); } @Test public void testFilterInclBootstrapClassesNegative() { options.setInclBootstrapClasses(false); CoverageTransformer t = createTransformer(); assertFalse(t.filter(null, "java/util/TreeSet", protectionDomain)); } @Test public void testFilterClassLoaderPositive1() { options.setInclBootstrapClasses(false); options.setExclClassloader("org.jacoco.agent.SomeWhere$*"); CoverageTransformer t = createTransformer(); assertTrue(t.filter(classLoader, "org/example/Foo", protectionDomain)); } @Test public void testFilterClassLoaderPositive2() { options.setInclBootstrapClasses(true); options.setExclClassloader("org.jacoco.agent.SomeWhere$*"); CoverageTransformer t = createTransformer(); assertTrue(t.filter(classLoader, "org/example/Foo", protectionDomain)); } @Test public void testFilterClassLoaderNegative1() { options.setInclBootstrapClasses(false); options.setExclClassloader( "org.jacoco.agent.rt.internal.CoverageTransformerTest$*"); CoverageTransformer t = createTransformer(); ClassLoader myClassLoader = new ClassLoader(null) { }; assertFalse( t.filter(myClassLoader, "org/example/Foo", protectionDomain)); } @Test public void testFilterClassLoaderNegative2() { options.setInclBootstrapClasses(true); options.setExclClassloader( "org.jacoco.agent.rt.internal.CoverageTransformerTest$*"); CoverageTransformer t = createTransformer(); ClassLoader myClassLoader = new ClassLoader(null) { }; assertFalse( t.filter(myClassLoader, "org/example/Foo", protectionDomain)); } @Test public void testFilterIncludedClassPositive() { options.setIncludes("org.jacoco.core.*:org.jacoco.agent.rt.*"); CoverageTransformer t = createTransformer(); assertTrue( t.filter(classLoader, "org/jacoco/core/Foo", protectionDomain)); } @Test public void testFilterIncludedClassNegative() { options.setIncludes("org.jacoco.core.*:org.jacoco.agent.rt.*"); CoverageTransformer t = createTransformer(); assertFalse(t.filter(classLoader, "org/jacoco/report/Foo", protectionDomain)); } @Test public void testFilterExcludedClassPositive() { options.setExcludes("*Test"); CoverageTransformer t = createTransformer(); assertFalse(t.filter(classLoader, "org/jacoco/core/FooTest", protectionDomain)); } @Test public void testFilterExcludedClassPositiveInner() { options.setExcludes("org.jacoco.example.Foo$Inner"); CoverageTransformer t = createTransformer(); assertFalse(t.filter(classLoader, "org/jacoco/example/Foo$Inner", protectionDomain)); } @Test public void testFilterExcludedClassNegative() { options.setExcludes("*Test"); CoverageTransformer t = createTransformer(); assertTrue( t.filter(classLoader, "org/jacoco/core/Foo", protectionDomain)); } @Test public void testFilterSourceLocationPositive1() { CoverageTransformer t = createTransformer(); assertFalse(t.filter(classLoader, "org/jacoco/core/Foo", null)); } @Test public void testFilterSourceLocationPositive2() { CoverageTransformer t = createTransformer(); ProtectionDomain pd = new ProtectionDomain(null, null); assertFalse(t.filter(classLoader, "org/jacoco/core/Foo", pd)); } @Test public void testFilterSourceLocationPositive3() { CoverageTransformer t = createTransformer(); CodeSource cs = new CodeSource(null, new Certificate[0]); ProtectionDomain pd = new ProtectionDomain(cs, null); assertFalse(t.filter(classLoader, "org/jacoco/core/Foo", pd)); } @Test public void testFilterSourceLocationNegative() { options.setInclNoLocationClasses(true); CoverageTransformer t = createTransformer(); assertTrue(t.filter(classLoader, "org/jacoco/core/Foo", null)); } @Test public void testTransformFiltered1() throws IllegalClassFormatException { CoverageTransformer t = createTransformer(); assertNull(t.transform(classLoader, "org.jacoco.Sample", null, null, new byte[0])); } @Test public void testTransformFiltered2() throws IllegalClassFormatException { CoverageTransformer t = createTransformer(); assertNull(t.transform((ClassLoader) null, "org.jacoco.Sample", null, protectionDomain, new byte[0])); } @Test public void testTransformFailure() { CoverageTransformer t = createTransformer(); try { t.transform(classLoader, "org.jacoco.Sample", null, protectionDomain, null); fail("IllegalClassFormatException expected."); } catch (IllegalClassFormatException e) { assertEquals(String.format( "Error while instrumenting %s with JaCoCo %s/%s.", "org.jacoco.Sample", JaCoCo.VERSION, JaCoCo.COMMITID_SHORT), e.getMessage()); } recorder.assertException(IllegalClassFormatException.class, String.format("Error while instrumenting %s with JaCoCo %s/%s.", "org.jacoco.Sample", JaCoCo.VERSION, JaCoCo.COMMITID_SHORT), IOException.class); recorder.clear(); } @Test public void testRedefinedClass() throws Exception { CoverageTransformer t = createTransformer(); // Just pick any non-system class outside our namespace final Class target = JaCoCo.class; assertNull(t.transform(classLoader, target.getName(), target, protectionDomain, getClassData(target))); } private CoverageTransformer createTransformer() { return new CoverageTransformer(runtime, options, recorder); } private static byte[] getClassData(Class clazz) throws IOException { final String resource = "/" + clazz.getName().replace('.', '/') + ".class"; final InputStream in = clazz.getResourceAsStream(resource); final ByteArrayOutputStream out = new ByteArrayOutputStream(); byte[] buffer = new byte[0x100]; int len; while ((len = in.read(buffer)) != -1) { out.write(buffer, 0, len); } in.close(); return out.toByteArray(); } private static class StubRuntime extends AbstractRuntime { public StubRuntime() { } public int generateDataAccessor(long classid, String classname, int probecount, MethodVisitor mv) { return 0; } public void shutdown() { } } } jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/ExceptionRecorder.java000066400000000000000000000033351451257705100322370ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNull; /** * {@link IExceptionLogger} implementation for testing purposes. */ public class ExceptionRecorder implements IExceptionLogger { private Class exceptionType; private String message; private Class causeType; public void logExeption(Exception ex) { assertNull("multiple exeptions", exceptionType); exceptionType = ex.getClass(); message = ex.getMessage(); causeType = ex.getCause() == null ? null : ex.getCause().getClass(); } public void clear() { exceptionType = null; message = null; causeType = null; } public void assertNoException() { assertNull(exceptionType); } public void assertException(final Class exceptionType, final String message) { assertEquals(exceptionType, this.exceptionType); assertEquals(message, this.message); } public void assertException(final Class exceptionType, final String message, final Class causeType) { assertEquals(exceptionType, this.exceptionType); assertEquals(message, this.message); assertEquals(causeType, this.causeType); } } jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/agent-subst-test.properties000066400000000000000000000002061451257705100332710ustar00rootroot00000000000000key0=no$replace} key1=${user.home}/coverage/jacoco-${java.version}.exec key2=$${user.home} key3=${user.home}}} key4=${does.not.exist} jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/agent-test.properties000066400000000000000000000000331451257705100321310ustar00rootroot00000000000000output=tcpclient port=3333 jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/output/000077500000000000000000000000001451257705100273045ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/output/ExecutorTestBase.java000066400000000000000000000031031451257705100333750ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import static org.junit.Assert.fail; import java.util.concurrent.Executor; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Future; import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeoutException; import org.junit.After; import org.junit.Before; /** * Unit tests base for tests that need an {@link Executor} for multithreaded * test scenarios. */ public abstract class ExecutorTestBase { protected ExecutorService executor; @Before public void setup() throws Exception { executor = Executors.newSingleThreadExecutor(); } @After public void teardown() throws Exception { executor.shutdown(); } /** * Asserts that the given future blocks. * * @param future * future to test * @throws Exception */ protected void assertBlocks(final Future future) throws Exception { try { future.get(10, TimeUnit.MILLISECONDS); fail("Operation should block"); } catch (TimeoutException e) { } } } jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/output/FileOutputTest.java000066400000000000000000000103221451257705100331050ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.InterruptedIOException; import java.nio.channels.OverlappingFileLockException; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.RuntimeData; import org.jacoco.core.test.validation.JavaVersion; import org.junit.AssumptionViolatedException; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TemporaryFolder; /** * Unit tests for {@link FileOutput}. */ public class FileOutputTest { @Rule public TemporaryFolder folder = new TemporaryFolder(); @Test public void startup_should_create_empty_execfile() throws Exception { File destFile = folder.newFile("jacoco.exec"); AgentOptions options = new AgentOptions(); options.setDestfile(destFile.getAbsolutePath()); FileOutput controller = new FileOutput(); controller.startup(options, new RuntimeData()); assertTrue("Execution data file should be created", destFile.exists()); assertEquals("Execution data file should be empty", 0, destFile.length()); } @Test public void writeExecutionData_should_write_execdata() throws Exception { File destFile = folder.newFile("jacoco.exec"); AgentOptions options = new AgentOptions(); options.setDestfile(destFile.getAbsolutePath()); FileOutput controller = new FileOutput(); controller.startup(options, new RuntimeData()); controller.writeExecutionData(false); controller.shutdown(); assertTrue("Execution data file should be created", destFile.exists()); assertTrue("Execution data file should have contents", destFile.length() > 0); } @Test public void startup_should_throw_IOException_when_execfile_cannot_be_created() throws Exception { AgentOptions options = new AgentOptions(); options.setDestfile(folder.newFolder("folder").getAbsolutePath()); FileOutput controller = new FileOutput(); try { controller.startup(options, new RuntimeData()); fail("IOException expected"); } catch (IOException e) { // expected } } @Test public void startup_should_throw_OverlappingFileLockException_when_execfile_is_permanently_locked() throws Exception { if (JavaVersion.current().isBefore("1.6")) { throw new AssumptionViolatedException( "OverlappingFileLockException only thrown since Java 1.6"); } File destFile = folder.newFile("jacoco.exec"); AgentOptions options = new AgentOptions(); options.setDestfile(destFile.getAbsolutePath()); FileOutputStream out = new FileOutputStream(destFile); out.getChannel().lock(); FileOutput controller = new FileOutput(); try { controller.startup(options, new RuntimeData()); fail("OverlappingFileLockException expected"); } catch (OverlappingFileLockException e) { // expected } finally { out.close(); } } public void startup_should_throw_InterruptedIOException_when_execfile_is_locked_and_thread_is_interrupted() throws Exception { if (JavaVersion.current().isBefore("1.6")) { throw new AssumptionViolatedException( "OverlappingFileLockException only thrown since Java 1.6"); } File destFile = folder.newFile("jacoco.exec"); AgentOptions options = new AgentOptions(); options.setDestfile(destFile.getAbsolutePath()); FileOutputStream out = new FileOutputStream(destFile); out.getChannel().lock(); FileOutput controller = new FileOutput(); Thread.currentThread().interrupt(); try { controller.startup(options, new RuntimeData()); fail("InterruptedIOException expected"); } catch (InterruptedIOException e) { // expected } finally { out.close(); } } } jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/output/MockServerSocket.java000066400000000000000000000100261451257705100333770ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import java.io.IOException; import java.io.InterruptedIOException; import java.net.InetAddress; import java.net.ServerSocket; import java.net.Socket; import java.net.SocketAddress; import java.net.SocketException; import java.nio.channels.ServerSocketChannel; /** * Emulation of a {@link ServerSocket} for testing purposes without any physical * tcp/ip connections. */ public class MockServerSocket extends ServerSocket { private final Object lock = new Object(); private boolean closed; private Socket connection; private boolean inAccept; public MockServerSocket() throws IOException { super(); closed = false; inAccept = false; } /** * Establishes a new mock connection. This method blocks until the other end * of the connection has been accepted. * * @return remote end of the mock connection */ public Socket connect() throws Exception { synchronized (lock) { final MockSocketConnection c = new MockSocketConnection(); connection = c.getSocketA(); lock.notifyAll(); while (connection != null) { lock.wait(); } return c.getSocketB(); } } /** * Blocks until another thread calls the {@link #accept()} method. */ public void waitForAccept() throws Exception { synchronized (lock) { while (!inAccept) { lock.wait(); } } } @Override public void close() throws IOException { synchronized (lock) { closed = true; lock.notifyAll(); } } @Override public boolean isClosed() { return closed; } @Override public Socket accept() throws IOException { synchronized (lock) { inAccept = true; lock.notifyAll(); try { while (connection == null) { if (closed) { throw new SocketException("socket closed"); } lock.wait(); } return connection; } catch (InterruptedException e) { throw new InterruptedIOException(); } finally { connection = null; inAccept = false; lock.notifyAll(); } } } // unsupported server socket methods: @Override public void bind(SocketAddress endpoint, int backlog) throws IOException { throw new AssertionError(); } @Override public void bind(SocketAddress endpoint) throws IOException { throw new AssertionError(); } @Override public ServerSocketChannel getChannel() { throw new AssertionError(); } @Override public InetAddress getInetAddress() { throw new AssertionError(); } @Override public int getLocalPort() { throw new AssertionError(); } @Override public SocketAddress getLocalSocketAddress() { throw new AssertionError(); } @Override public synchronized int getReceiveBufferSize() throws SocketException { throw new AssertionError(); } @Override public boolean getReuseAddress() throws SocketException { throw new AssertionError(); } @Override public synchronized int getSoTimeout() throws IOException { throw new AssertionError(); } @Override public boolean isBound() { throw new AssertionError(); } @Override public void setPerformancePreferences(int connectionTime, int latency, int bandwidth) { throw new AssertionError(); } @Override public synchronized void setReceiveBufferSize(int size) throws SocketException { throw new AssertionError(); } @Override public void setReuseAddress(boolean on) throws SocketException { throw new AssertionError(); } @Override public synchronized void setSoTimeout(int timeout) throws SocketException { throw new AssertionError(); } @Override public String toString() { throw new AssertionError(); } } MockServerSocketTest.java000066400000000000000000000076711451257705100341740ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/output/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertTrue; import java.net.InetAddress; import java.net.ServerSocket; import java.net.Socket; import java.net.SocketException; import java.util.concurrent.Callable; import java.util.concurrent.ExecutionException; import java.util.concurrent.Future; import org.junit.After; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link MockServerSocket}. */ public class MockServerSocketTest extends ExecutorTestBase { private ServerSocket serverSocket; /** * To verify that the tests reflect the behavior of real TCP sockets this * flag can be set to true. */ private static final boolean REAL_SOCKETS = Boolean .getBoolean("MockServerSocketTest.realSockets"); @Before @Override public void setup() throws Exception { super.setup(); if (REAL_SOCKETS) { System.err.println("Using Real Sockets!"); final InetAddress addr = InetAddress.getByName("localhost"); serverSocket = new ServerSocket(16300, 1, addr); } else { serverSocket = new MockServerSocket(); } } @After @Override public void teardown() throws Exception { serverSocket.close(); super.teardown(); } private Socket connect() throws Exception { if (REAL_SOCKETS) { final InetAddress addr = InetAddress.getByName("localhost"); return new Socket(addr, 16300); } else { return ((MockServerSocket) serverSocket).connect(); } } @Test public void testClose() throws Exception { assertFalse(serverSocket.isClosed()); serverSocket.close(); assertTrue(serverSocket.isClosed()); } @Test(expected = SocketException.class) public void testCloseWhileAccept() throws Throwable { final Future f = executor.submit(new Callable() { public Socket call() throws Exception { return serverSocket.accept(); } }); assertBlocks(f); serverSocket.close(); try { f.get(); } catch (ExecutionException e) { throw e.getCause(); } } @Test public void testAccept() throws Exception { final Future f = executor.submit(new Callable() { public Socket call() throws Exception { return serverSocket.accept(); } }); assertBlocks(f); connect().getOutputStream().write(123); final Socket socket = f.get(); assertNotNull(socket); assertEquals(123, socket.getInputStream().read()); } @Test(expected = SocketException.class) public void testAcceptOnClosedServerSocket() throws Exception { serverSocket.close(); serverSocket.accept(); } @Test public void testConnect() throws Exception { if (!REAL_SOCKETS) { final Future f = executor.submit(new Callable() { public Socket call() throws Exception { return ((MockServerSocket) serverSocket).connect(); } }); assertBlocks(f); serverSocket.accept().getOutputStream().write(42); final Socket socket = f.get(); assertNotNull(socket); assertEquals(42, socket.getInputStream().read()); } } @Test public void testWaitForAccept() throws Exception { if (!REAL_SOCKETS) { final Future f = executor.submit(new Callable() { public Void call() throws Exception { ((MockServerSocket) serverSocket).waitForAccept(); connect(); return null; } }); assertBlocks(f); serverSocket.accept(); f.get(); } } } MockSocketConnection.java000066400000000000000000000167441451257705100341660ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/output/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import java.io.IOException; import java.io.InputStream; import java.io.InterruptedIOException; import java.io.OutputStream; import java.net.InetAddress; import java.net.Socket; import java.net.SocketAddress; import java.net.SocketException; import java.net.SocketImpl; import java.nio.channels.SocketChannel; import java.util.Queue; import java.util.concurrent.ConcurrentLinkedQueue; /** * Simulates two connected {@link Socket} objects. No physical connection is * established for this. The behavior includes the (inconsistent) exception * messages have been derived from Sun JDK 1.5.0_18-b02. */ public class MockSocketConnection { private final MockSocket socketA; private final MockSocket socketB; public MockSocketConnection() throws SocketException { socketA = new MockSocket(); socketB = new MockSocket(); socketA.connect(socketB); } public MockSocket getSocketA() { return socketA; } public MockSocket getSocketB() { return socketB; } class MockSocket extends Socket { private MockSocket other; private boolean closed; private final Queue buffer = new ConcurrentLinkedQueue(); private final OutputStream out = new OutputStream() { @Override public void write(int b) throws IOException { if (closed) { throw new SocketException("Socket closed"); } synchronized (other.buffer) { other.buffer.add(Byte.valueOf((byte) b)); other.buffer.notifyAll(); } } }; private final InputStream in = new InputStream() { @Override public int read() throws IOException { synchronized (buffer) { try { while (true) { if (closed) { throw new SocketException("socket closed"); } if (other.closed) { return -1; } final Byte b = buffer.poll(); buffer.notifyAll(); if (b != null) { return 0xff & b.intValue(); } buffer.wait(); } } catch (InterruptedException e) { throw new InterruptedIOException(); } } } @Override public int available() throws IOException { synchronized (buffer) { return buffer.size(); } } }; private MockSocket() throws SocketException { super((SocketImpl) null); closed = false; } private void connect(MockSocket other) { this.other = other; other.other = this; } public void waitUntilInputBufferIsEmpty() throws InterruptedException { synchronized (buffer) { while (!closed && !buffer.isEmpty()) { buffer.wait(); } } } // socket methods with mocking behavior: @Override public OutputStream getOutputStream() throws IOException { if (isClosed()) { throw new SocketException("Socket is closed"); } return out; } @Override public InputStream getInputStream() throws IOException { if (isClosed()) { throw new SocketException("Socket is closed"); } return in; } @Override public void close() throws IOException { synchronized (buffer) { closed = true; buffer.notifyAll(); } synchronized (other.buffer) { other.buffer.notifyAll(); } } @Override public boolean isClosed() { synchronized (buffer) { return closed; } } // unsupported socket methods: @Override public void bind(SocketAddress bindpoint) throws IOException { throw new AssertionError(); } @Override public void connect(SocketAddress endpoint, int timeout) throws IOException { throw new AssertionError(); } @Override public void connect(SocketAddress endpoint) throws IOException { throw new AssertionError(); } @Override public SocketChannel getChannel() { throw new AssertionError(); } @Override public InetAddress getInetAddress() { throw new AssertionError(); } @Override public boolean getKeepAlive() throws SocketException { throw new AssertionError(); } @Override public InetAddress getLocalAddress() { throw new AssertionError(); } @Override public int getLocalPort() { throw new AssertionError(); } @Override public SocketAddress getLocalSocketAddress() { throw new AssertionError(); } @Override public boolean getOOBInline() throws SocketException { throw new AssertionError(); } @Override public int getPort() { throw new AssertionError(); } @Override public synchronized int getReceiveBufferSize() throws SocketException { throw new AssertionError(); } @Override public SocketAddress getRemoteSocketAddress() { throw new AssertionError(); } @Override public boolean getReuseAddress() throws SocketException { throw new AssertionError(); } @Override public synchronized int getSendBufferSize() throws SocketException { throw new AssertionError(); } @Override public int getSoLinger() throws SocketException { throw new AssertionError(); } @Override public synchronized int getSoTimeout() throws SocketException { throw new AssertionError(); } @Override public boolean getTcpNoDelay() throws SocketException { throw new AssertionError(); } @Override public int getTrafficClass() throws SocketException { throw new AssertionError(); } @Override public boolean isBound() { throw new AssertionError(); } @Override public boolean isConnected() { throw new AssertionError(); } @Override public boolean isInputShutdown() { throw new AssertionError(); } @Override public boolean isOutputShutdown() { throw new AssertionError(); } @Override public void sendUrgentData(int data) throws IOException { throw new AssertionError(); } @Override public void setKeepAlive(boolean on) throws SocketException { throw new AssertionError(); } @Override public void setOOBInline(boolean on) throws SocketException { throw new AssertionError(); } @Override public void setPerformancePreferences(int connectionTime, int latency, int bandwidth) { throw new AssertionError(); } @Override public synchronized void setReceiveBufferSize(int size) throws SocketException { throw new AssertionError(); } @Override public void setReuseAddress(boolean on) throws SocketException { throw new AssertionError(); } @Override public synchronized void setSendBufferSize(int size) throws SocketException { throw new AssertionError(); } @Override public void setSoLinger(boolean on, int linger) throws SocketException { throw new AssertionError(); } @Override public synchronized void setSoTimeout(int timeout) throws SocketException { throw new AssertionError(); } @Override public void setTcpNoDelay(boolean on) throws SocketException { throw new AssertionError(); } @Override public void setTrafficClass(int tc) throws SocketException { throw new AssertionError(); } @Override public void shutdownInput() throws IOException { throw new AssertionError(); } @Override public void shutdownOutput() throws IOException { throw new AssertionError(); } } } MockSocketConnectionTest.java000066400000000000000000000110751451257705100350160ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/output/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import java.io.InputStream; import java.io.OutputStream; import java.net.InetAddress; import java.net.ServerSocket; import java.net.Socket; import java.net.SocketException; import java.util.concurrent.Callable; import java.util.concurrent.ExecutionException; import java.util.concurrent.Future; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link MockSocketConnection}. */ public class MockSocketConnectionTest extends ExecutorTestBase { /** * To verify that the tests reflect the behavior of real TCP sockets this * flag can be set to true. */ private static final boolean REAL_SOCKETS = Boolean .getBoolean("MockSocketConnectionTest.realSockets"); private Socket a; private Socket b; @Before @Override public void setup() throws Exception { super.setup(); if (REAL_SOCKETS) { createRealSockets(); } else { createMockSockets(); } } private void createMockSockets() throws Exception { final MockSocketConnection con = new MockSocketConnection(); a = con.getSocketA(); b = con.getSocketB(); } private void createRealSockets() throws Exception { System.err.println("Using Real Sockets!"); final InetAddress addr = InetAddress.getByName("localhost"); ServerSocket ssocket = new ServerSocket(16300, 1, addr); a = new Socket(addr, 16300); b = ssocket.accept(); ssocket.close(); } @Test public void testIsClosed() throws Exception { assertFalse(a.isClosed()); a.close(); assertTrue(a.isClosed()); } @Test(expected = SocketException.class) public void testGetInputStreamOnClosedSocket() throws Exception { a.close(); a.getInputStream(); } @Test(expected = SocketException.class) public void testReadOnClosedSocket() throws Exception { final InputStream in = a.getInputStream(); a.close(); in.read(); } @Test(expected = SocketException.class) public void testReadOnClosedSocketAsync() throws Throwable { final InputStream in = a.getInputStream(); final Future f = executor.submit(new Callable() { public Void call() throws Exception { in.read(); return null; } }); assertBlocks(f); a.close(); try { f.get(); } catch (ExecutionException e) { throw e.getCause(); } } @Test(expected = SocketException.class) public void testGetOutputStreamOnClosedSocket() throws Exception { a.close(); a.getOutputStream(); } @Test(expected = SocketException.class) public void testWriteOnClosedSocket() throws Exception { final OutputStream out = a.getOutputStream(); a.close(); out.write(123); } @Test public void testContents() throws Exception { final InputStream in = a.getInputStream(); final OutputStream out = b.getOutputStream(); assertEquals(0, in.available()); out.write(0); out.write(1); out.write(2); out.write(255); if (!REAL_SOCKETS) { // Real sockets will have a delay assertEquals(4, in.available()); } assertEquals(0, in.read()); assertEquals(1, in.read()); assertEquals(2, in.read()); assertEquals(255, in.read()); } @Test public void testWaitForContents() throws Exception { final InputStream in = a.getInputStream(); final OutputStream out = b.getOutputStream(); final Future f = executor.submit(new Callable() { public Byte call() throws Exception { return Byte.valueOf((byte) in.read()); } }); assertBlocks(f); out.write(123); assertEquals(123, f.get().byteValue()); } @Test public void testCloseOtherSocket() throws Exception { b.close(); final InputStream in = a.getInputStream(); assertEquals(-1, in.read()); } @Test public void testCloseOtherSocketAsync() throws Exception { final InputStream in = a.getInputStream(); final Future f = executor.submit(new Callable() { public Byte call() throws Exception { return Byte.valueOf((byte) in.read()); } }); assertBlocks(f); b.close(); assertEquals(-1, f.get().byteValue()); } } TcpClientOutputTest.java000066400000000000000000000070711451257705100340430ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/output/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * Marc R. Hoffmann - migration to mock socket * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import java.io.IOException; import java.net.Socket; import java.util.List; import org.jacoco.agent.rt.internal.ExceptionRecorder; import org.jacoco.agent.rt.internal.output.MockSocketConnection.MockSocket; import org.jacoco.core.data.ExecutionDataStore; import org.jacoco.core.data.SessionInfo; import org.jacoco.core.data.SessionInfoStore; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.RemoteControlReader; import org.jacoco.core.runtime.RemoteControlWriter; import org.jacoco.core.runtime.RuntimeData; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link TcpClientOutput}. */ public class TcpClientOutputTest { private ExceptionRecorder logger; private IAgentOutput controller; private MockSocket localSocket; private MockSocket remoteSocket; private RemoteControlWriter remoteWriter; private RemoteControlReader remoteReader; private RuntimeData data; @Before public void setup() throws Exception { logger = new ExceptionRecorder(); final MockSocketConnection con = new MockSocketConnection(); localSocket = con.getSocketA(); remoteSocket = con.getSocketB(); remoteWriter = new RemoteControlWriter(remoteSocket.getOutputStream()); controller = new TcpClientOutput(logger) { @Override protected Socket createSocket(AgentOptions options) throws IOException { return localSocket; } }; data = new RuntimeData(); controller.startup(new AgentOptions(), data); remoteReader = new RemoteControlReader(remoteSocket.getInputStream()); } @Test public void testShutdown() throws Exception { controller.shutdown(); assertFalse(remoteReader.read()); logger.assertNoException(); } @Test public void testRemoteClose() throws Exception { localSocket.waitUntilInputBufferIsEmpty(); remoteSocket.close(); controller.shutdown(); logger.assertNoException(); } @Test public void testInvalidCommand() throws Exception { // send invalid command to agent remoteWriter.visitSessionInfo(new SessionInfo("info", 1, 2)); localSocket.waitUntilInputBufferIsEmpty(); controller.shutdown(); logger.assertException(IOException.class, "No session info visitor."); } @Test public void testWriteExecutionData() throws Exception { data.getExecutionData(Long.valueOf(0x12345678), "Foo", 42) .getProbes()[0] = true; data.setSessionId("stubid"); controller.writeExecutionData(false); final ExecutionDataStore execStore = new ExecutionDataStore(); remoteReader.setExecutionDataVisitor(execStore); final SessionInfoStore infoStore = new SessionInfoStore(); remoteReader.setSessionInfoVisitor(infoStore); remoteReader.read(); assertEquals("Foo", execStore.get(0x12345678).getName()); final List infos = infoStore.getInfos(); assertEquals(1, infos.size()); assertEquals("stubid", infos.get(0).getId()); logger.assertNoException(); controller.shutdown(); } } TcpConnectionTest.java000066400000000000000000000154601451257705100335040ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/output/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import java.io.IOException; import java.io.OutputStream; import java.util.List; import java.util.concurrent.Callable; import java.util.concurrent.Future; import org.jacoco.core.data.ExecutionDataStore; import org.jacoco.core.data.ExecutionDataWriter; import org.jacoco.core.data.SessionInfo; import org.jacoco.core.data.SessionInfoStore; import org.jacoco.core.runtime.RemoteControlReader; import org.jacoco.core.runtime.RemoteControlWriter; import org.jacoco.core.runtime.RuntimeData; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link TcpConnection}. */ public class TcpConnectionTest extends ExecutorTestBase { private MockSocketConnection mockConnection; private RuntimeData data; @Before @Override public void setup() throws Exception { super.setup(); mockConnection = new MockSocketConnection(); data = new RuntimeData(); } @Test(expected = IOException.class) public void testInvalidHeader() throws Exception { final OutputStream remoteOut = mockConnection.getSocketB() .getOutputStream(); remoteOut.write(0x01); remoteOut.write(0xC0); remoteOut.write(0xCA); final TcpConnection connection = new TcpConnection( mockConnection.getSocketA(), data); connection.init(); connection.run(); } @Test(expected = IOException.class) public void testInvalidContent() throws Exception { final OutputStream remoteOut = mockConnection.getSocketB() .getOutputStream(); new ExecutionDataWriter(remoteOut); final TcpConnection con = new TcpConnection(mockConnection.getSocketA(), data); con.init(); remoteOut.write(123); con.run(); } /** * Remote endpoint is closed after a valid header has been send. */ @Test public void testRemoteClose() throws Exception { final OutputStream remoteOut = mockConnection.getSocketB() .getOutputStream(); new ExecutionDataWriter(remoteOut); final TcpConnection con = new TcpConnection(mockConnection.getSocketA(), data); con.init(); final Future f = executor.submit(new Callable() { public Void call() throws Exception { con.run(); return null; } }); assertBlocks(f); mockConnection.getSocketA().waitUntilInputBufferIsEmpty(); mockConnection.getSocketB().close(); f.get(); } /** * Local socket is closed while waiting for commands. * * @throws Exception */ @Test public void testLocalClose() throws Exception { final OutputStream remoteOut = mockConnection.getSocketB() .getOutputStream(); new ExecutionDataWriter(remoteOut); final TcpConnection con = new TcpConnection(mockConnection.getSocketA(), data); con.init(); final Future f = executor.submit(new Callable() { public Void call() throws Exception { con.run(); return null; } }); assertBlocks(f); con.close(); f.get(); } @Test public void testRemoteDump() throws Exception { data.getExecutionData(Long.valueOf(0x12345678), "Foo", 42) .getProbes()[0] = true; data.setSessionId("stubid"); final RemoteControlWriter remoteWriter = new RemoteControlWriter( mockConnection.getSocketB().getOutputStream()); final TcpConnection con = new TcpConnection(mockConnection.getSocketA(), data); con.init(); final Future f = executor.submit(new Callable() { public Void call() throws Exception { con.run(); return null; } }); assertBlocks(f); remoteWriter.visitDumpCommand(true, false); readAndAssertData(); con.close(); f.get(); } @Test public void testLocalDump() throws Exception { data.getExecutionData(Long.valueOf(0x12345678), "Foo", 42) .getProbes()[0] = true; data.setSessionId("stubid"); new RemoteControlWriter(mockConnection.getSocketB().getOutputStream()); final TcpConnection con = new TcpConnection(mockConnection.getSocketA(), data); con.init(); final Future f = executor.submit(new Callable() { public Void call() throws Exception { con.run(); return null; } }); assertBlocks(f); con.writeExecutionData(false); readAndAssertData(); con.close(); f.get(); } @Test public void testLocalDumpWithoutInit() throws Exception { final TcpConnection con = new TcpConnection(mockConnection.getSocketA(), data); // Must not write any data as we're not initialized: con.writeExecutionData(false); assertEquals(0, mockConnection.getSocketB().getInputStream().available()); } private void readAndAssertData() throws IOException { final RemoteControlReader remoteReader = new RemoteControlReader( mockConnection.getSocketB().getInputStream()); final ExecutionDataStore execStore = new ExecutionDataStore(); remoteReader.setExecutionDataVisitor(execStore); final SessionInfoStore infoStore = new SessionInfoStore(); remoteReader.setSessionInfoVisitor(infoStore); assertTrue(remoteReader.read()); final List infos = infoStore.getInfos(); assertEquals(1, infos.size()); assertEquals("stubid", infos.get(0).getId()); assertEquals("Foo", execStore.get(0x12345678).getName()); } @Test public void testRemoteReset() throws Exception { data.getExecutionData(Long.valueOf(123), "Foo", 1) .getProbes()[0] = true; final RemoteControlWriter remoteWriter = new RemoteControlWriter( mockConnection.getSocketB().getOutputStream()); final TcpConnection con = new TcpConnection(mockConnection.getSocketA(), data); con.init(); final Future f = executor.submit(new Callable() { public Void call() throws Exception { con.run(); return null; } }); assertBlocks(f); remoteWriter.visitDumpCommand(false, true); final RemoteControlReader remoteReader = new RemoteControlReader( mockConnection.getSocketB().getInputStream()); final ExecutionDataStore execStore = new ExecutionDataStore(); remoteReader.setExecutionDataVisitor(execStore); final SessionInfoStore infoStore = new SessionInfoStore(); remoteReader.setSessionInfoVisitor(infoStore); assertTrue(remoteReader.read()); assertTrue(infoStore.getInfos().isEmpty()); assertTrue(execStore.getContents().isEmpty()); assertFalse(data.getExecutionData(Long.valueOf(123), "Foo", 1) .getProbes()[0]); con.close(); f.get(); } } TcpServerOutputTest.java000066400000000000000000000104431451257705100340700ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt.test/src/org/jacoco/agent/rt/internal/output/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * Marc R. Hoffmann - migration to mock socket * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import java.io.IOException; import java.io.OutputStream; import java.net.InetAddress; import java.net.ServerSocket; import java.net.Socket; import java.net.UnknownHostException; import java.util.List; import org.jacoco.agent.rt.internal.ExceptionRecorder; import org.jacoco.core.data.ExecutionDataStore; import org.jacoco.core.data.ExecutionDataWriter; import org.jacoco.core.data.SessionInfo; import org.jacoco.core.data.SessionInfoStore; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.RemoteControlReader; import org.jacoco.core.runtime.RemoteControlWriter; import org.jacoco.core.runtime.RuntimeData; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link TcpServerOutput}. */ public class TcpServerOutputTest { private ExceptionRecorder logger; private AgentOptions options; private MockServerSocket serverSocket; private TcpServerOutput controller; private RuntimeData data; @Before public void setup() throws Exception { options = new AgentOptions(); logger = new ExceptionRecorder(); serverSocket = new MockServerSocket(); controller = new TcpServerOutput(logger) { @Override protected ServerSocket createServerSocket(AgentOptions options) throws IOException { return serverSocket; } }; data = new RuntimeData(); controller.startup(options, data); } @Test public void testShutdownWithoutConnection() throws Exception { serverSocket.waitForAccept(); controller.shutdown(); logger.assertNoException(); } @Test public void testShutdownWithConnection() throws Exception { serverSocket.waitForAccept(); new ExecutionDataWriter(serverSocket.connect().getOutputStream()); controller.shutdown(); logger.assertNoException(); } @Test public void testWriteExecutionData() throws Exception { data.getExecutionData(Long.valueOf(0x12345678), "Foo", 42) .getProbes()[0] = true; data.setSessionId("stubid"); final Socket socket = serverSocket.connect(); final RemoteControlWriter remoteWriter = new RemoteControlWriter( socket.getOutputStream()); final RemoteControlReader remoteReader = new RemoteControlReader( socket.getInputStream()); // First process a NOP command to ensure the connection is initialized: remoteWriter.visitDumpCommand(false, false); remoteReader.read(); // Now the actual test starts: controller.writeExecutionData(false); final ExecutionDataStore execStore = new ExecutionDataStore(); remoteReader.setExecutionDataVisitor(execStore); final SessionInfoStore infoStore = new SessionInfoStore(); remoteReader.setSessionInfoVisitor(infoStore); remoteReader.read(); assertEquals("Foo", execStore.get(0x12345678).getName()); final List infos = infoStore.getInfos(); assertEquals(1, infos.size()); assertEquals("stubid", infos.get(0).getId()); logger.assertNoException(); controller.shutdown(); } @Test public void testInvalidHeader() throws Exception { final Socket socket = serverSocket.connect(); final OutputStream out = socket.getOutputStream(); out.write(0xca); out.write(0xfe); out.write(0xba); out.write(0xbe); serverSocket.waitForAccept(); logger.assertException(IOException.class, "Invalid execution data file."); controller.shutdown(); } @Test public void testGetInetAddressLoopback() throws UnknownHostException { final InetAddress addr = controller.getInetAddress(null); assertTrue(addr.isLoopbackAddress()); } @Test public void testGetInetAddressAny() throws UnknownHostException { final InetAddress addr = controller.getInetAddress("*"); assertNull(addr); } } jacoco-0.8.11/org.jacoco.agent.rt/000077500000000000000000000000001451257705100166135ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt/.classpath000066400000000000000000000014151451257705100205770ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.agent.rt/.project000066400000000000000000000013651451257705100202670ustar00rootroot00000000000000 org.jacoco.agent.rt org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core/.settings jacoco-0.8.11/org.jacoco.agent.rt/about.html000066400000000000000000000017221451257705100206150ustar00rootroot00000000000000 About

About This Content

${build.date}

License

All Content in this distribution is made available by Mountainminds GmbH & Co. KG, Munich. Unless otherwise indicated below, the Content is provided to you under the terms and conditions of the Eclipse Public License Version 2.0 ("EPL"). A copy of the EPL is available at https://www.eclipse.org/legal/epl-2.0/. For purposes of the EPL, "Program" will mean the Content.

Third Party Content

The Content includes items that have been sourced from third parties as set out below.

${asm.license} jacoco-0.8.11/org.jacoco.agent.rt/pom.xml000066400000000000000000000071521451257705100201350ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.build 0.8.11 ../org.jacoco.build org.jacoco.agent.rt JaCoCo :: Agent RT JaCoCo Java Agent true true ${project.groupId} org.jacoco.core src org.apache.maven.plugins maven-shade-plugin package shade true all true org.jacoco.agent.rt.internal ${jacoco.runtime.package.name} org.jacoco.core ${jacoco.runtime.package.name}.core org.objectweb.asm ${jacoco.runtime.package.name}.asm org.ow2.asm:* module-info.class ${jacoco.runtime.package.name}.PreMain ${project.artifactId} ${project.description} ${project.organization.name} ${project.version} jacoco-0.8.11/org.jacoco.agent.rt/src/000077500000000000000000000000001451257705100174025ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt/src/com/000077500000000000000000000000001451257705100201605ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt/src/com/vladium/000077500000000000000000000000001451257705100216215ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt/src/com/vladium/emma/000077500000000000000000000000001451257705100225405ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt/src/com/vladium/emma/rt/000077500000000000000000000000001451257705100231655ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt/src/com/vladium/emma/rt/RT.java000066400000000000000000000044341451257705100243620ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package com.vladium.emma.rt; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.OutputStream; /** * Compatibility layer for the EMMA runtime which allows to trigger dumps * through EMMA APIs. Note that even this class emulates an EMMA API the files * written are in JaCoCo execution data format. * * @deprecated Use {@link org.jacoco.agent.rt.IAgent} instead. */ @Deprecated public final class RT { private RT() { } /** * Writes the current execution data to the given file in JaCoCo execution * data format. * * @param outFile * file to write execution data to * @param merge * if true, execution data is appended to an * existing file * @param stopDataCollection * ignored * @throws IOException * in case of problems with the file output */ @SuppressWarnings("unused") public static void dumpCoverageData(final File outFile, final boolean merge, final boolean stopDataCollection) throws IOException { final OutputStream out = new FileOutputStream(outFile, merge); try { out.write( org.jacoco.agent.rt.RT.getAgent().getExecutionData(false)); } finally { out.close(); } } /** * Writes the current execution data to the given file in JaCoCo execution * data format. If the file already exists new data is appended. * * @param outFile * file to write execution data to * @param stopDataCollection * ignored * @throws IOException * in case of problems with the file output */ public static synchronized void dumpCoverageData(final File outFile, final boolean stopDataCollection) throws IOException { dumpCoverageData(outFile, true, stopDataCollection); } } jacoco-0.8.11/org.jacoco.agent.rt/src/com/vladium/emma/rt/package-info.java000066400000000000000000000011441451257705100263540ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ /** * Compatibility API for EMMA runtime. */ package com.vladium.emma.rt; jacoco-0.8.11/org.jacoco.agent.rt/src/org/000077500000000000000000000000001451257705100201715ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/000077500000000000000000000000001451257705100214275ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/000077500000000000000000000000001451257705100225255ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/000077500000000000000000000000001451257705100231525ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/IAgent.java000066400000000000000000000032471451257705100251720ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt; import java.io.IOException; /** * Runtime API and MBean agent interface. */ public interface IAgent { /** * Returns version of JaCoCo. * * @return version of JaCoCo */ String getVersion(); /** * Returns current a session identifier. * * @return current session identifier */ String getSessionId(); /** * Sets a session identifier. * * @param id * new session identifier */ void setSessionId(String id); /** * Resets all coverage information. */ void reset(); /** * Returns current execution data. * * @param reset * if true the current execution data is cleared * afterwards * @return dump of current execution data in JaCoCo binary format */ byte[] getExecutionData(boolean reset); /** * Triggers a dump of the current execution data through the configured * output. * * @param reset * if true the current execution data is cleared * afterwards * @throws IOException * if the output can't write execution data */ void dump(boolean reset) throws IOException; } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/RT.java000066400000000000000000000017531451257705100243500ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt; import org.jacoco.agent.rt.internal.Agent; /** * Entry point to access the JaCoCo agent runtime. */ public final class RT { private RT() { } /** * Returns the agent instance of the JaCoCo runtime in this JVM. * * @return agent instance * @throws IllegalStateException * if no Agent has been started yet */ public static IAgent getAgent() throws IllegalStateException { return Agent.getInstance(); } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/000077500000000000000000000000001451257705100247665ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/Agent.java000066400000000000000000000132131451257705100266670ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.net.InetAddress; import java.util.concurrent.Callable; import org.jacoco.agent.rt.IAgent; import org.jacoco.agent.rt.internal.output.FileOutput; import org.jacoco.agent.rt.internal.output.IAgentOutput; import org.jacoco.agent.rt.internal.output.NoneOutput; import org.jacoco.agent.rt.internal.output.TcpClientOutput; import org.jacoco.agent.rt.internal.output.TcpServerOutput; import org.jacoco.core.JaCoCo; import org.jacoco.core.data.ExecutionDataWriter; import org.jacoco.core.runtime.AbstractRuntime; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.AgentOptions.OutputMode; import org.jacoco.core.runtime.RuntimeData; /** * The agent manages the life cycle of JaCoCo runtime. */ public class Agent implements IAgent { private static Agent singleton; /** * Returns a global instance which is already started. If the method is * called the first time the instance is created with the given options. * * @param options * options to configure the instance * @return global instance * @throws Exception * in case something cannot be initialized */ public static synchronized Agent getInstance(final AgentOptions options) throws Exception { if (singleton == null) { final Agent agent = new Agent(options, IExceptionLogger.SYSTEM_ERR); agent.startup(); Runtime.getRuntime().addShutdownHook(new Thread() { @Override public void run() { agent.shutdown(); } }); singleton = agent; } return singleton; } /** * Returns a global instance which is already started. If a agent has not * been initialized before this method will fail. * * @return global instance * @throws IllegalStateException * if no Agent has been started yet */ public static synchronized Agent getInstance() throws IllegalStateException { if (singleton == null) { throw new IllegalStateException("JaCoCo agent not started."); } return singleton; } private final AgentOptions options; private final IExceptionLogger logger; private final RuntimeData data; private IAgentOutput output; private Callable jmxRegistration; /** * Creates a new agent with the given agent options. * * @param options * agent options * @param logger * logger used by this agent */ Agent(final AgentOptions options, final IExceptionLogger logger) { this.options = options; this.logger = logger; this.data = new RuntimeData(); } /** * Returns the runtime data object created by this agent * * @return runtime data for this agent instance */ public RuntimeData getData() { return data; } /** * Initializes this agent. * * @throws Exception * in case something cannot be initialized */ public void startup() throws Exception { try { String sessionId = options.getSessionId(); if (sessionId == null) { sessionId = createSessionId(); } data.setSessionId(sessionId); output = createAgentOutput(); output.startup(options, data); if (options.getJmx()) { jmxRegistration = new JmxRegistration(this); } } catch (final Exception e) { logger.logExeption(e); throw e; } } /** * Shutdown the agent again. */ public void shutdown() { try { if (options.getDumpOnExit()) { output.writeExecutionData(false); } output.shutdown(); if (jmxRegistration != null) { jmxRegistration.call(); } } catch (final Exception e) { logger.logExeption(e); } } /** * Create output implementation as given by the agent options. * * @return configured controller implementation */ IAgentOutput createAgentOutput() { final OutputMode controllerType = options.getOutput(); switch (controllerType) { case file: return new FileOutput(); case tcpserver: return new TcpServerOutput(logger); case tcpclient: return new TcpClientOutput(logger); case none: return new NoneOutput(); default: throw new AssertionError(controllerType); } } private String createSessionId() { String host; try { host = InetAddress.getLocalHost().getHostName(); } catch (final Exception e) { // Also catch platform specific exceptions (like on Android) to // avoid bailing out here host = "unknownhost"; } return host + "-" + AbstractRuntime.createRandomId(); } // === IAgent Implementation === public String getVersion() { return JaCoCo.VERSION; } public String getSessionId() { return data.getSessionId(); } public void setSessionId(final String id) { data.setSessionId(id); } public void reset() { data.reset(); } public byte[] getExecutionData(final boolean reset) { final ByteArrayOutputStream buffer = new ByteArrayOutputStream(); try { final ExecutionDataWriter writer = new ExecutionDataWriter(buffer); data.collect(writer, writer, reset); } catch (final IOException e) { // Must not happen with ByteArrayOutputStream throw new AssertionError(e); } return buffer.toByteArray(); } public void dump(final boolean reset) throws IOException { output.writeExecutionData(reset); } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/AgentModule.java000066400000000000000000000114511451257705100300370ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * Marc R. Hoffmann - move to separate class * *******************************************************************************/ package org.jacoco.agent.rt.internal; import java.io.IOException; import java.io.InputStream; import java.lang.instrument.Instrumentation; import java.util.Collections; import java.util.HashSet; import java.util.Map; import java.util.Set; import org.jacoco.core.internal.InputStreams; /** * An isolated class loader and distinct module to encapsulate JaCoCo runtime * classes. This isolated environment allows to specifically open JDK packages * to the agent runtime without changing package accessibility for the * application under test. *

* The implementation uses the property that the * unnamed module is distinct from all run-time modules (including unnamed * modules) bound to other class loaders. */ public class AgentModule { /** * Checks whether Java modules are supported by the current Java runtime. * * @return true is modules are supported */ public static boolean isSupported() { try { getModuleClass(); } catch (final ClassNotFoundException e) { return false; } return true; } private final Set scope = new HashSet(); private final ClassLoader classLoader; /** * Creates a new isolated module. * * @throws Exception * if it cannot be created */ public AgentModule() throws Exception { classLoader = new ClassLoader() { @Override protected Class loadClass(final String name, final boolean resolve) throws ClassNotFoundException { if (!scope.contains(name)) { return super.loadClass(name, resolve); } final InputStream resourceAsStream = getResourceAsStream( name.replace('.', '/') + ".class"); final byte[] bytes; try { bytes = InputStreams.readFully(resourceAsStream); } catch (final IOException e) { throw new RuntimeException(e); } return defineClass(name, bytes, 0, bytes.length, AgentModule.class.getProtectionDomain()); } }; } /** * Opens the package of the provided class to the module created in this * {@link #AgentModule()} instance. * * @param instrumentation * service provided to the agent by the Java runtime * @param classInPackage * example class of the package to open * @throws Exception * if package cannot be opened */ public void openPackage(final Instrumentation instrumentation, final Class classInPackage) throws Exception { // module of the package to open final Object module = Class.class.getMethod("getModule") .invoke(classInPackage); // unnamed module of our classloader final Object unnamedModule = ClassLoader.class .getMethod("getUnnamedModule").invoke(classLoader); // Open package java.lang to the unnamed module of our class loader Instrumentation.class.getMethod("redefineModule", // getModuleClass(), // Set.class, // Map.class, // Map.class, // Set.class, // Map.class // ).invoke(instrumentation, // instance module, // module Collections.emptySet(), // extraReads Collections.emptyMap(), // extraExports Collections.singletonMap(classInPackage.getPackage().getName(), Collections.singleton(unnamedModule)), // extraOpens Collections.emptySet(), // extraUses Collections.emptyMap() // extraProvides ); } /** * Loads a copy of the given class in the isolated classloader. Also any * inner classes are loader from the isolated classloader. * * @param * type of the class to load * @param original * original class definition which is used as source * @return class object from the isolated class loader * @throws Exception * if the class cannot be loaded */ @SuppressWarnings("unchecked") public Class loadClassInModule(final Class original) throws Exception { addToScopeWithInnerClasses(original); return (Class) classLoader.loadClass(original.getName()); } private void addToScopeWithInnerClasses(final Class c) { scope.add(c.getName()); for (final Class i : c.getDeclaredClasses()) { addToScopeWithInnerClasses(i); } } private static Class getModuleClass() throws ClassNotFoundException { return Class.forName("java.lang.Module"); } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/ClassFileDumper.java000066400000000000000000000042051451257705100306540ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.OutputStream; import org.jacoco.core.internal.data.CRC64; /** * Internal dumper for class files. */ class ClassFileDumper { private final File location; /** * Create a new dumper for the given location. * * @param location * relative path to dump directory. null if no dumps * should be written */ ClassFileDumper(final String location) { if (location == null) { this.location = null; } else { this.location = new File(location); } } /** * Dumps the given binary content under the given name if a non- * null location has been specified. * * @param name * qualified class name in VM notation * @param contents * binary contents * @throws IOException * in case of problems while dumping the file */ void dump(final String name, final byte[] contents) throws IOException { if (location != null) { final File outputdir; final String localname; final int pkgpos = name.lastIndexOf('/'); if (pkgpos != -1) { outputdir = new File(location, name.substring(0, pkgpos)); localname = name.substring(pkgpos + 1); } else { outputdir = location; localname = name; } outputdir.mkdirs(); final Long id = Long.valueOf(CRC64.classId(contents)); final File file = new File(outputdir, String.format("%s.%016x.class", localname, id)); final OutputStream out = new FileOutputStream(file); out.write(contents); out.close(); } } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/ConfigLoader.java000066400000000000000000000053141451257705100301700ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; import java.io.IOException; import java.io.InputStream; import java.util.Map; import java.util.Properties; import java.util.regex.Matcher; import java.util.regex.Pattern; /** * Internal utility to load runtime configuration from a classpath resource and * from system properties. System property keys are prefixed with * jacoco.. If the same property is defined twice the system * property takes precedence. */ final class ConfigLoader { private static final String SYS_PREFIX = "jacoco-agent."; private static final Pattern SUBST_PATTERN = Pattern .compile("\\$\\{([^\\}]+)\\}"); static Properties load(final String resource, final Properties system) { final Properties result = new Properties(); loadResource(resource, result); loadSystemProperties(system, result); substSystemProperties(result, system); return result; } private static void loadResource(final String resource, final Properties result) { final InputStream file = Offline.class.getResourceAsStream(resource); if (file != null) { try { result.load(file); } catch (final IOException e) { throw new RuntimeException(e); } } } private static void loadSystemProperties(final Properties system, final Properties result) { for (final Map.Entry entry : system.entrySet()) { final String keystr = entry.getKey().toString(); if (keystr.startsWith(SYS_PREFIX)) { result.put(keystr.substring(SYS_PREFIX.length()), entry.getValue()); } } } private static void substSystemProperties(final Properties result, final Properties system) { for (final Map.Entry entry : result.entrySet()) { final String oldValue = (String) entry.getValue(); final StringBuilder newValue = new StringBuilder(); final Matcher m = SUBST_PATTERN.matcher(oldValue); int pos = 0; while (m.find()) { newValue.append(oldValue.substring(pos, m.start())); final String sub = system.getProperty(m.group(1)); newValue.append(sub == null ? m.group(0) : sub); pos = m.end(); } newValue.append(oldValue.substring(pos)); entry.setValue(newValue.toString()); } } private ConfigLoader() { } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/CoverageTransformer.java000066400000000000000000000113421451257705100316100ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; import java.lang.instrument.ClassFileTransformer; import java.lang.instrument.IllegalClassFormatException; import java.security.CodeSource; import java.security.ProtectionDomain; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.IRuntime; import org.jacoco.core.runtime.WildcardMatcher; /** * Class file transformer to instrument classes for code coverage analysis. */ public class CoverageTransformer implements ClassFileTransformer { private static final String AGENT_PREFIX; static { final String name = CoverageTransformer.class.getName(); AGENT_PREFIX = toVMName(name.substring(0, name.lastIndexOf('.'))); } private final Instrumenter instrumenter; private final IExceptionLogger logger; private final WildcardMatcher includes; private final WildcardMatcher excludes; private final WildcardMatcher exclClassloader; private final ClassFileDumper classFileDumper; private final boolean inclBootstrapClasses; private final boolean inclNoLocationClasses; /** * New transformer with the given delegates. * * @param runtime * coverage runtime * @param options * configuration options for the generator * @param logger * logger for exceptions during instrumentation */ public CoverageTransformer(final IRuntime runtime, final AgentOptions options, final IExceptionLogger logger) { this.instrumenter = new Instrumenter(runtime); this.logger = logger; // Class names will be reported in VM notation: includes = new WildcardMatcher(toVMName(options.getIncludes())); excludes = new WildcardMatcher(toVMName(options.getExcludes())); exclClassloader = new WildcardMatcher(options.getExclClassloader()); classFileDumper = new ClassFileDumper(options.getClassDumpDir()); inclBootstrapClasses = options.getInclBootstrapClasses(); inclNoLocationClasses = options.getInclNoLocationClasses(); } public byte[] transform(final ClassLoader loader, final String classname, final Class classBeingRedefined, final ProtectionDomain protectionDomain, final byte[] classfileBuffer) throws IllegalClassFormatException { // We do not support class retransformation: if (classBeingRedefined != null) { return null; } if (!filter(loader, classname, protectionDomain)) { return null; } try { classFileDumper.dump(classname, classfileBuffer); return instrumenter.instrument(classfileBuffer, classname); } catch (final Exception ex) { final IllegalClassFormatException wrapper = new IllegalClassFormatException( ex.getMessage()); wrapper.initCause(ex); // Report this, as the exception is ignored by the JVM: logger.logExeption(wrapper); throw wrapper; } } /** * Checks whether this class should be instrumented. * * @param loader * loader for the class * @param classname * VM name of the class to check * @param protectionDomain * protection domain for the class * @return true if the class should be instrumented */ boolean filter(final ClassLoader loader, final String classname, final ProtectionDomain protectionDomain) { if (loader == null) { if (!inclBootstrapClasses) { return false; } } else { if (!inclNoLocationClasses && !hasSourceLocation(protectionDomain)) { return false; } if (exclClassloader.matches(loader.getClass().getName())) { return false; } } return !classname.startsWith(AGENT_PREFIX) && includes.matches(classname) && !excludes.matches(classname); } /** * Checks whether this protection domain is associated with a source * location. * * @param protectionDomain * protection domain to check (or null) * @return true if a source location is defined */ private boolean hasSourceLocation(final ProtectionDomain protectionDomain) { if (protectionDomain == null) { return false; } final CodeSource codeSource = protectionDomain.getCodeSource(); if (codeSource == null) { return false; } return codeSource.getLocation() != null; } private static String toVMName(final String srcName) { return srcName.replace('.', '/'); } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/IExceptionLogger.java000066400000000000000000000021171451257705100310410ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; /** * At several places exception might occur that should be reported. For * testability these exceptions are emitted against this interface. */ public interface IExceptionLogger { /** * Default implementation which dumps the stack trace to System.err. */ IExceptionLogger SYSTEM_ERR = new IExceptionLogger() { public void logExeption(final Exception ex) { ex.printStackTrace(); } }; /** * Logs the given exception. * * @param ex * exception to log */ void logExeption(Exception ex); } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/JmxRegistration.java000066400000000000000000000027231451257705100307660ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; import java.lang.management.ManagementFactory; import java.util.concurrent.Callable; import javax.management.MBeanServer; import javax.management.ObjectName; import javax.management.StandardMBean; import org.jacoco.agent.rt.IAgent; /** * Access to JMX APIs are encapsulated in this class to allow the JaCoCo runtime * on platforms without JMX support (e.g Android). */ class JmxRegistration implements Callable { private static final String JMX_NAME = "org.jacoco:type=Runtime"; private final MBeanServer server; private final ObjectName name; JmxRegistration(final IAgent agent) throws Exception { server = ManagementFactory.getPlatformMBeanServer(); name = new ObjectName(JMX_NAME); server.registerMBean(new StandardMBean(agent, IAgent.class), name); } /** * De-register the agent again. */ public Void call() throws Exception { server.unregisterMBean(name); return null; } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/Offline.java000066400000000000000000000035721451257705100272220ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; import java.util.Properties; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.RuntimeData; /** * The API for classes instrumented in "offline" mode. The agent configuration * is provided through system properties prefixed with jacoco.. */ public final class Offline { private static final String CONFIG_RESOURCE = "/jacoco-agent.properties"; private Offline() { // no instances } private static RuntimeData data; private static synchronized RuntimeData getRuntimeData() { if (data == null) { final Properties config = ConfigLoader.load(CONFIG_RESOURCE, System.getProperties()); try { data = Agent.getInstance(new AgentOptions(config)).getData(); } catch (final Exception e) { throw new RuntimeException("Failed to initialize JaCoCo.", e); } } return data; } /** * API for offline instrumented classes. * * @param classid * class identifier * @param classname * VM class name * @param probecount * probe count for this class * @return probe array instance for this class */ public static boolean[] getProbes(final long classid, final String classname, final int probecount) { return getRuntimeData() .getExecutionData(Long.valueOf(classid), classname, probecount) .getProbes(); } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/PreMain.java000066400000000000000000000043141451257705100271660ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal; import java.lang.instrument.Instrumentation; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.IRuntime; import org.jacoco.core.runtime.InjectedClassRuntime; import org.jacoco.core.runtime.ModifiedSystemClassRuntime; /** * The agent which is referred as the Premain-Class. The agent * configuration is provided with the agent parameters in the command line. */ public final class PreMain { private PreMain() { // no instances } /** * This method is called by the JVM to initialize Java agents. * * @param options * agent options * @param inst * instrumentation callback provided by the JVM * @throws Exception * in case initialization fails */ public static void premain(final String options, final Instrumentation inst) throws Exception { final AgentOptions agentOptions = new AgentOptions(options); final Agent agent = Agent.getInstance(agentOptions); final IRuntime runtime = createRuntime(inst); runtime.startup(agent.getData()); inst.addTransformer(new CoverageTransformer(runtime, agentOptions, IExceptionLogger.SYSTEM_ERR)); } private static IRuntime createRuntime(final Instrumentation inst) throws Exception { if (AgentModule.isSupported()) { final AgentModule module = new AgentModule(); module.openPackage(inst, Object.class); final Class clazz = module .loadClassInModule(InjectedClassRuntime.class); return clazz.getConstructor(Class.class, String.class) .newInstance(Object.class, "$JaCoCo"); } return ModifiedSystemClassRuntime.createFor(inst, "java/lang/UnknownError"); } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/output/000077500000000000000000000000001451257705100263265ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/output/FileOutput.java000066400000000000000000000057301451257705100312760ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.InterruptedIOException; import java.io.OutputStream; import java.nio.channels.FileChannel; import java.nio.channels.OverlappingFileLockException; import org.jacoco.core.data.ExecutionDataWriter; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.RuntimeData; /** * Local only agent output that will write coverage data to the filesystem. This * controller uses the following agent options: *

    *
  • destfile
  • *
  • append
  • *
*/ public class FileOutput implements IAgentOutput { private static final int LOCK_RETRY_COUNT = 30; private static final long LOCK_RETRY_WAIT_TIME_MS = 100; private RuntimeData data; private File destFile; private boolean append; public final void startup(final AgentOptions options, final RuntimeData data) throws IOException { this.data = data; this.destFile = new File(options.getDestfile()).getAbsoluteFile(); this.append = options.getAppend(); final File folder = destFile.getParentFile(); if (folder != null) { folder.mkdirs(); } // Make sure we can write to the file: openFile().close(); } public void writeExecutionData(final boolean reset) throws IOException { final OutputStream output = openFile(); try { final ExecutionDataWriter writer = new ExecutionDataWriter(output); data.collect(writer, writer, reset); } finally { output.close(); } } public void shutdown() throws IOException { // Nothing to do } private OutputStream openFile() throws IOException { final FileOutputStream file = new FileOutputStream(destFile, append); // Avoid concurrent writes from different agents running in parallel: final FileChannel fc = file.getChannel(); int retries = 0; while (true) { try { // An agent from another JVM might have a lock. In this case // this method blocks until the lock is freed. fc.lock(); return file; } catch (final OverlappingFileLockException e) { // In the case of multiple class loaders there can be multiple // JaCoCo runtimes even in the same VM. In this case we get an // OverlappingFileLockException and retry lock acquisition: if (retries++ > LOCK_RETRY_COUNT) { throw e; } } try { Thread.sleep(LOCK_RETRY_WAIT_TIME_MS); } catch (final InterruptedException e) { throw new InterruptedIOException(); } } } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/output/IAgentOutput.java000066400000000000000000000033661451257705100315710ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import java.io.IOException; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.RuntimeData; /** * Common interface for different implementations that outputs execution data * dumps. */ public interface IAgentOutput { /** * Configure the agent controller with the supplied options and connect it * to the coverage runtime * * @param options * Options used to configure the agent controller * @param data * Execution data for this agent * @throws Exception * in case startup fails */ void startup(AgentOptions options, RuntimeData data) throws Exception; /** * Shutdown the agent controller and clean up any resources it has created. * * @throws Exception * in case shutdown fails */ void shutdown() throws Exception; /** * Write all execution data in the runtime to a location determined by the * agent controller. This method should only be called by the Agent * * @param reset * if true execution data is cleared afterwards * @throws IOException * in case writing fails */ void writeExecutionData(boolean reset) throws IOException; } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/output/NoneOutput.java000066400000000000000000000017431451257705100313160ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Mandrikov Evgeny - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.RuntimeData; /** * Output that does nothing. */ public class NoneOutput implements IAgentOutput { public final void startup(final AgentOptions options, final RuntimeData data) { // Nothing to do } public void writeExecutionData(final boolean reset) { // Nothing to do } public void shutdown() { // Nothing to do } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/output/TcpClientOutput.java000066400000000000000000000044171451257705100323050ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import java.io.IOException; import java.net.Socket; import org.jacoco.agent.rt.internal.IExceptionLogger; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.RuntimeData; /** * Output that connects to a TCP port. This controller uses the following agent * options: *
    *
  • address
  • *
  • port
  • *
*/ public class TcpClientOutput implements IAgentOutput { private final IExceptionLogger logger; private TcpConnection connection; private Thread worker; /** * New controller instance. * * @param logger * logger to use in case of exceptions is spawned threads */ public TcpClientOutput(final IExceptionLogger logger) { this.logger = logger; } public void startup(final AgentOptions options, final RuntimeData data) throws IOException { final Socket socket = createSocket(options); connection = new TcpConnection(socket, data); connection.init(); worker = new Thread(new Runnable() { public void run() { try { connection.run(); } catch (final IOException e) { logger.logExeption(e); } } }); worker.setName(getClass().getName()); worker.setDaemon(true); worker.start(); } public void shutdown() throws Exception { connection.close(); worker.join(); } public void writeExecutionData(final boolean reset) throws IOException { connection.writeExecutionData(reset); } /** * Open a socket based on the given configuration. * * @param options * address and port configuration * @return opened socket * @throws IOException */ protected Socket createSocket(final AgentOptions options) throws IOException { return new Socket(options.getAddress(), options.getPort()); } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/output/TcpConnection.java000066400000000000000000000055101451257705100317400ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import java.io.IOException; import java.net.Socket; import java.net.SocketException; import org.jacoco.core.runtime.IRemoteCommandVisitor; import org.jacoco.core.runtime.RemoteControlReader; import org.jacoco.core.runtime.RemoteControlWriter; import org.jacoco.core.runtime.RuntimeData; /** * Handler for a single socket based remote connection. */ class TcpConnection implements IRemoteCommandVisitor { private final RuntimeData data; private final Socket socket; private RemoteControlWriter writer; private RemoteControlReader reader; private boolean initialized; public TcpConnection(final Socket socket, final RuntimeData data) { this.socket = socket; this.data = data; this.initialized = false; } public void init() throws IOException { this.writer = new RemoteControlWriter(socket.getOutputStream()); this.reader = new RemoteControlReader(socket.getInputStream()); this.reader.setRemoteCommandVisitor(this); this.initialized = true; } /** * Processes all requests for this session until the socket is closed. * * @throws IOException * in case of problems whith the connection */ public void run() throws IOException { try { while (reader.read()) { } } catch (final SocketException e) { // If the local socket is closed while polling for commands the // SocketException is expected. if (!socket.isClosed()) { throw e; } } finally { close(); } } /** * Dumps the current execution data if the connection is already initialized * and the underlying socket is still open. * * @param reset * if true execution data is cleared afterwards * @throws IOException */ public void writeExecutionData(final boolean reset) throws IOException { if (initialized && !socket.isClosed()) { visitDumpCommand(true, reset); } } /** * Closes the underlying socket if not closed yet. * * @throws IOException */ public void close() throws IOException { if (!socket.isClosed()) { socket.close(); } } // === IRemoteCommandVisitor === public void visitDumpCommand(final boolean dump, final boolean reset) throws IOException { if (dump) { data.collect(writer, writer, reset); } else { if (reset) { data.reset(); } } writer.sendCmdOk(); } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/internal/output/TcpServerOutput.java000066400000000000000000000064411451257705100323340ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent.rt.internal.output; import java.io.IOException; import java.net.InetAddress; import java.net.ServerSocket; import java.net.UnknownHostException; import org.jacoco.agent.rt.internal.IExceptionLogger; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.RuntimeData; /** * Output that opens TCP server socket. This controller uses the following agent * options: *
    *
  • address
  • *
  • port
  • *
*/ public class TcpServerOutput implements IAgentOutput { private TcpConnection connection; private final IExceptionLogger logger; private ServerSocket serverSocket; private Thread worker; /** * New controller instance. * * @param logger * logger to use in case of exceptions is spawned threads */ public TcpServerOutput(final IExceptionLogger logger) { this.logger = logger; } public void startup(final AgentOptions options, final RuntimeData data) throws IOException { serverSocket = createServerSocket(options); worker = new Thread(new Runnable() { public void run() { while (!serverSocket.isClosed()) { try { synchronized (serverSocket) { connection = new TcpConnection( serverSocket.accept(), data); } connection.init(); connection.run(); } catch (final IOException e) { // If the serverSocket is closed while accepting // connections a SocketException is expected. if (!serverSocket.isClosed()) { logger.logExeption(e); } } } } }); worker.setName(getClass().getName()); worker.setDaemon(true); worker.start(); } public void shutdown() throws Exception { serverSocket.close(); synchronized (serverSocket) { if (connection != null) { connection.close(); } } worker.join(); } public void writeExecutionData(final boolean reset) throws IOException { if (connection != null) { connection.writeExecutionData(reset); } } /** * Open a server socket based on the given configuration. * * @param options * address and port configuration * @return opened server socket * @throws IOException */ protected ServerSocket createServerSocket(final AgentOptions options) throws IOException { final InetAddress inetAddr = getInetAddress(options.getAddress()); return new ServerSocket(options.getPort(), 1, inetAddr); } /** * Returns the {@link InetAddress} object to open the server socket on. * * @param address * address specified as a string * @return address to open the server socket * @throws UnknownHostException */ protected InetAddress getInetAddress(final String address) throws UnknownHostException { if ("*".equals(address)) { return null; } else { return InetAddress.getByName(address); } } } jacoco-0.8.11/org.jacoco.agent.rt/src/org/jacoco/agent/rt/package-info.java000066400000000000000000000011771451257705100263470ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ /** * API to access the JaCoCo agent from within the JVM under test. */ package org.jacoco.agent.rt; jacoco-0.8.11/org.jacoco.agent.test/000077500000000000000000000000001451257705100171455ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.test/.classpath000066400000000000000000000014151451257705100211310ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.agent.test/.project000066400000000000000000000013361451257705100206170ustar00rootroot00000000000000 org.jacoco.agent.test org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.agent.test/pom.xml000066400000000000000000000024201451257705100204600ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.tests 0.8.11 ../org.jacoco.tests org.jacoco.agent.test JaCoCo :: Test :: Agent org.jacoco.agent.* ${project.groupId} org.jacoco.agent junit junit jacoco-0.8.11/org.jacoco.agent.test/src/000077500000000000000000000000001451257705100177345ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.test/src/org/000077500000000000000000000000001451257705100205235ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.test/src/org/jacoco/000077500000000000000000000000001451257705100217615ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.test/src/org/jacoco/agent/000077500000000000000000000000001451257705100230575ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent.test/src/org/jacoco/agent/AgentJarTest.java000066400000000000000000000046361451257705100262660ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNotNull; import java.io.File; import java.io.FileInputStream; import java.io.IOException; import java.io.InputStream; import java.util.jar.Manifest; import java.util.zip.ZipEntry; import java.util.zip.ZipInputStream; import org.junit.After; import org.junit.Test; /** * Unit tests for {@link AgentJar}. */ public class AgentJarTest { private File file; @After public void teardown() { if (file != null) { file.delete(); } } @Test public void testGetResource() throws IOException { final InputStream in = AgentJar.getResource().openStream(); assertAgentContents(in); } @Test public void testGetResourceAsStream() throws IOException { final InputStream in = AgentJar.getResourceAsStream(); assertAgentContents(in); } @Test public void testExtractTo() throws IOException { file = File.createTempFile("agent", ".jar"); AgentJar.extractTo(file); assertAgentContents(new FileInputStream(file)); } @Test(expected = IOException.class) public void testExtractToNegative() throws IOException { file = File.createTempFile("folder", null); file.delete(); file.mkdirs(); AgentJar.extractTo(file); } @Test public void testExtractToTempLocation() throws IOException { file = AgentJar.extractToTempLocation(); assertAgentContents(new FileInputStream(file)); file.delete(); } private void assertAgentContents(InputStream in) throws IOException { final ZipInputStream zip = new ZipInputStream(in); while (true) { final ZipEntry entry = zip.getNextEntry(); assertNotNull("Manifest not found.", entry); if ("META-INF/MANIFEST.MF".equals(entry.getName())) { final Manifest manifest = new Manifest(zip); assertEquals("JaCoCo Java Agent", manifest.getMainAttributes() .getValue("Implementation-Title")); in.close(); break; } } } } jacoco-0.8.11/org.jacoco.agent/000077500000000000000000000000001451257705100161675ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent/.classpath000066400000000000000000000014151451257705100201530ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.agent/.project000066400000000000000000000016431451257705100176420ustar00rootroot00000000000000 org.jacoco.agent org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.jdt.core.javanature org.eclipse.m2e.core.maven2Nature src/jacocoagent.jar 1 PARENT-1-PROJECT_LOC/org.jacoco.agent/target/classes/jacocoagent.jar .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core/.settings jacoco-0.8.11/org.jacoco.agent/README.TXT000066400000000000000000000010041451257705100175200ustar00rootroot00000000000000This bundle provides the coverage agent "jacocoagent.jar" as a resource. The agent JAR is created as part of the build process and therefore not available in the source tree. Which means this bundle is incomplete when directly used in the Eclise IDE. If you want to use the bundle org.jacoco.agent within the IDE, please run the local build (see documentation) first. The jacocoagent.jar file is created by the build at /org.jacoco.agent/target/classes/jacocoagent.jar and linked by this project. jacoco-0.8.11/org.jacoco.agent/about.html000066400000000000000000000017221451257705100201710ustar00rootroot00000000000000 About

About This Content

${build.date}

License

All Content in this distribution is made available by Mountainminds GmbH & Co. KG, Munich. Unless otherwise indicated below, the Content is provided to you under the terms and conditions of the Eclipse Public License Version 2.0 ("EPL"). A copy of the EPL is available at https://www.eclipse.org/legal/epl-2.0/. For purposes of the EPL, "Program" will mean the Content.

Third Party Content

The Content includes items that have been sourced from third parties as set out below.

${asm.license} jacoco-0.8.11/org.jacoco.agent/pom.xml000066400000000000000000000066571451257705100175220ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.build 0.8.11 ../org.jacoco.build org.jacoco.agent JaCoCo :: Agent JaCoCo Agent src org.apache.maven.plugins maven-dependency-plugin prepare-package copy ${project.groupId} org.jacoco.agent.rt all ${project.version} jacocoagent.jar ${project.build.directory}/classes false false true org.codehaus.mojo build-helper-maven-plugin attach-artifacts package attach-artifact ${project.build.directory}/classes/jacocoagent.jar jar runtime org.apache.felix maven-bundle-plugin process-classes manifest org.apache.maven.plugins maven-jar-plugin ${project.build.outputDirectory}/META-INF/MANIFEST.MF jacoco-0.8.11/org.jacoco.agent/src/000077500000000000000000000000001451257705100167565ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent/src/org/000077500000000000000000000000001451257705100175455ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent/src/org/jacoco/000077500000000000000000000000001451257705100210035ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent/src/org/jacoco/agent/000077500000000000000000000000001451257705100221015ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.agent/src/org/jacoco/agent/AgentJar.java000066400000000000000000000066561451257705100244540ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.agent; import java.io.Closeable; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.net.URL; /** * API to access the agent JAR file as a resource. While the agent is a JAR file * it is considered as a plain resource that must be configured for the * application under test (target JVM). The agent JAR does not provide any * public Java API. */ public final class AgentJar { /** * Name of the agent JAR file resource within this bundle. */ private static final String RESOURCE = "/jacocoagent.jar"; private AgentJar() { } /** * Returns a URL pointing to the JAR file. * * @return URL of the JAR file */ public static URL getResource() { final URL url = AgentJar.class.getResource(RESOURCE); if (url == null) { throw new AssertionError(ERRORMSG); } return url; } /** * Returns the content of the JAR file as a stream. * * @return content of the JAR file */ public static InputStream getResourceAsStream() { final InputStream stream = AgentJar.class.getResourceAsStream(RESOURCE); if (stream == null) { throw new AssertionError(ERRORMSG); } return stream; } /** * Extract the JaCoCo agent JAR and put it into a temporary location. This * file should be deleted on exit, but may not if the VM is terminated * * @return Location of the Agent Jar file in the local file system. The file * should exist and be readable. * @throws IOException * Unable to unpack agent jar */ public static File extractToTempLocation() throws IOException { final File agentJar = File.createTempFile("jacocoagent", ".jar"); agentJar.deleteOnExit(); extractTo(agentJar); return agentJar; } /** * Extract the JaCoCo agent JAR and put it into the specified location. * * @param destination * Location to write JaCoCo Agent Jar to. Must be writeable * @throws IOException * Unable to unpack agent jar */ public static void extractTo(File destination) throws IOException { InputStream inputJarStream = getResourceAsStream(); OutputStream outputJarStream = null; try { outputJarStream = new FileOutputStream(destination); final byte[] buffer = new byte[8192]; int bytesRead; while ((bytesRead = inputJarStream.read(buffer)) != -1) { outputJarStream.write(buffer, 0, bytesRead); } } finally { safeClose(inputJarStream); safeClose(outputJarStream); } } /** * Close a stream ignoring any error * * @param closeable * stream to be closed */ private static void safeClose(Closeable closeable) { try { if (closeable != null) { closeable.close(); } } catch (IOException e) { } } private static final String ERRORMSG = String .format("The resource %s has not been found. Please see " + "/org.jacoco.agent/README.TXT for details.", RESOURCE); } jacoco-0.8.11/org.jacoco.agent/src/org/jacoco/agent/package-info.java000066400000000000000000000011671451257705100252750ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ /** * Provides the runtime Java agent (JAR file) as a resource. */ package org.jacoco.agent; jacoco-0.8.11/org.jacoco.ant.test/000077500000000000000000000000001451257705100166315ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.ant.test/.classpath000066400000000000000000000014151451257705100206150ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.ant.test/.project000066400000000000000000000013721451257705100203030ustar00rootroot00000000000000 org.jacoco.ant.test org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.ant.test/pom.xml000066400000000000000000000040311451257705100201440ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.tests 0.8.11 ../org.jacoco.tests org.jacoco.ant.test JaCoCo :: Test :: Ant org.jacoco.ant.* ${project.groupId} org.jacoco.ant junit junit org.apache.ant ant-antunit org.apache.ant ant-launcher org.apache.ant ant-junit org.apache.ant ant-junit4 org.apache.maven.plugins maven-surefire-plugin ${project.build.outputDirectory}/org/jacoco/ant jacoco-0.8.11/org.jacoco.ant.test/src/000077500000000000000000000000001451257705100174205ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.ant.test/src/TestTargetInDefault.java000066400000000000000000000011531451257705100241450ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ /** * Test target in default directory. */ public class TestTargetInDefault { } jacoco-0.8.11/org.jacoco.ant.test/src/org/000077500000000000000000000000001451257705100202075ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/000077500000000000000000000000001451257705100214455ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/000077500000000000000000000000001451257705100222275ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/AgentTaskTest.java000066400000000000000000000017331451257705100256170ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.io.File; import org.apache.ant.antunit.junit3.AntUnitSuite; import org.apache.ant.antunit.junit4.AntUnitSuiteRunner; import org.junit.runner.RunWith; import junit.framework.TestSuite; @RunWith(AntUnitSuiteRunner.class) public class AgentTaskTest { public static TestSuite suite() { final File file = new File("src/org/jacoco/ant/AgentTaskTest.xml"); return new AntUnitSuite(file, AgentTaskTest.class); } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/AgentTaskTest.xml000066400000000000000000000057431451257705100255030ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/AntFilesLocatorTest.java000066400000000000000000000044701451257705100267700ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertNull; import java.io.BufferedReader; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.OutputStreamWriter; import java.io.Reader; import java.io.Writer; import org.apache.tools.ant.types.Resource; import org.apache.tools.ant.types.resources.FileResource; import org.junit.Before; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TemporaryFolder; /** * Unit tests for {@link AntFilesLocator}. */ public class AntFilesLocatorTest { @Rule public final TemporaryFolder folder = new TemporaryFolder(); private AntFilesLocator locator; @Before public void setup() { locator = new AntFilesLocator("UTF-8", 4); } @Test public void testGetSourceFileNegative() throws IOException { assertNull(locator.getSourceFile("org/jacoco/somewhere", "DoesNotExist.java")); } @Test public void testGetSourceFile() throws IOException { locator.add(createFile("org/jacoco/example/Test.java")); final Reader source = locator.getSourceFile("org/jacoco/example", "Test.java"); assertContent(source); } private Resource createFile(String path) throws IOException { final File file = new File(folder.getRoot(), path); file.getParentFile().mkdirs(); final Writer writer = new OutputStreamWriter(new FileOutputStream(file), "UTF-8"); writer.write("Source"); writer.close(); return new FileResource(folder.getRoot(), path); } private void assertContent(Reader source) throws IOException { assertNotNull(source); final BufferedReader buffer = new BufferedReader(source); assertEquals("Source", buffer.readLine()); assertNull(buffer.readLine()); buffer.close(); } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/AntResourcesLocatorTest.java000066400000000000000000000104161451257705100276750ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import java.io.BufferedReader; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.OutputStreamWriter; import java.io.Reader; import java.io.Writer; import java.util.ArrayList; import java.util.List; import org.apache.tools.ant.types.Resource; import org.apache.tools.ant.types.resources.FileResource; import org.junit.Before; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TemporaryFolder; /** * Unit tests for {@link AntResourcesLocator}. */ public class AntResourcesLocatorTest { @Rule public final TemporaryFolder folder = new TemporaryFolder(); private AntResourcesLocator locator; @Before public void setup() { locator = new AntResourcesLocator("UTF-8", 8); } @Test public void testGetTabWidth() { assertEquals(8, locator.getTabWidth()); } @Test public void testEmpty() { assertTrue(locator.isEmpty()); } @Test public void testFile() throws IOException { locator.add(createFile("org/jacoco/example/Test.java", "AAA")); assertFalse(locator.isEmpty()); final Reader source = locator.getSourceFile("org/jacoco/example", "Test.java"); assertContent("AAA", source); } @Test public void testDirectory() throws IOException { createFile("src/org/jacoco/example/Test.java", "AAA"); locator.add(new FileResource(folder.getRoot(), "src")); assertFalse(locator.isEmpty()); final Reader source = locator.getSourceFile("org/jacoco/example", "Test.java"); assertContent("AAA", source); } @Test public void testFilePrecedence() throws IOException { createFile("src/org/jacoco/example/Test.java", "DDD"); locator.add(new FileResource(folder.getRoot(), "src")); locator.add(createFile("org/jacoco/example/Test.java", "FFF")); final Reader source = locator.getSourceFile("org/jacoco/example", "Test.java"); assertContent("FFF", source); } @Test public void testDirectoryOrdering() throws IOException { createFile("src1/org/jacoco/example/Test.java", "AAA"); locator.add(new FileResource(folder.getRoot(), "src1")); createFile("src2/org/jacoco/example/Test.java", "BBB"); locator.add(new FileResource(folder.getRoot(), "src2")); createFile("src3/org/jacoco/example/Test.java", "CCC"); locator.add(new FileResource(folder.getRoot(), "src3")); final Reader source = locator.getSourceFile("org/jacoco/example", "Test.java"); assertContent("AAA", source); } @Test public void testAddAll() throws IOException { List resources = new ArrayList(); resources.add(createFile("org/jacoco/example/Test1.java", "AAA")); resources.add(createFile("org/jacoco/example/Test2.java", "BBB")); locator.addAll(resources.iterator()); assertFalse(locator.isEmpty()); Reader source = locator.getSourceFile("org/jacoco/example", "Test1.java"); assertContent("AAA", source); source = locator.getSourceFile("org/jacoco/example", "Test2.java"); assertContent("BBB", source); } private Resource createFile(String path, String content) throws IOException { final File file = new File(folder.getRoot(), path); file.getParentFile().mkdirs(); final Writer writer = new OutputStreamWriter(new FileOutputStream(file), "UTF-8"); writer.write(content); writer.close(); return new FileResource(folder.getRoot(), path); } private void assertContent(String expected, Reader source) throws IOException { assertNotNull(source); final BufferedReader buffer = new BufferedReader(source); assertEquals(expected, buffer.readLine()); assertNull(buffer.readLine()); buffer.close(); } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/CoverageTaskTest.java000066400000000000000000000021101451257705100263020ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.io.File; import org.apache.ant.antunit.junit3.AntUnitSuite; import org.apache.ant.antunit.junit4.AntUnitSuiteRunner; import org.junit.runner.RunWith; import junit.framework.TestSuite; @RunWith(AntUnitSuiteRunner.class) public class CoverageTaskTest { public static TestSuite suite() { System.setProperty("org.jacoco.ant.coverageTaskTest.classes.dir", TestTarget.getClassPath()); final File file = new File("src/org/jacoco/ant/CoverageTaskTest.xml"); return new AntUnitSuite(file, CoverageTaskTest.class); } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/CoverageTaskTest.xml000066400000000000000000000151001451257705100261640ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/CreateExecFiles.java000066400000000000000000000027021451257705100260660ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.io.FileOutputStream; import java.io.IOException; import java.io.OutputStream; import org.jacoco.core.data.ExecutionData; import org.jacoco.core.data.ExecutionDataWriter; /** * Utility class to create exec files required for some Ant tests. */ public class CreateExecFiles { private static final String BASE_LOCATION = "./src/org/jacoco/ant/data/"; public static void main(String[] args) throws IOException { OutputStream out; out = new FileOutputStream(BASE_LOCATION + "sample1.exec"); new ExecutionDataWriter(out); out.close(); out = new FileOutputStream(BASE_LOCATION + "sample2.exec"); new ExecutionDataWriter(out); out.close(); out = new FileOutputStream(BASE_LOCATION + "nomatch.exec"); ExecutionDataWriter writer = new ExecutionDataWriter(out); writer.visitClassExecution(new ExecutionData(0, "org/jacoco/ant/TestTarget", new boolean[0])); out.close(); } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/DumpExecClassNames.java000066400000000000000000000020411451257705100265530ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.io.File; import org.jacoco.core.data.ExecutionData; import org.jacoco.core.tools.ExecFileLoader; /** * Test utility to dump class names from exec file. */ public class DumpExecClassNames { public static void main(String[] args) throws Exception { final ExecFileLoader loader = new ExecFileLoader(); for (String f : args) { loader.load(new File(f)); } for (ExecutionData d : loader.getExecutionDataStore().getContents()) { System.out.println(d.getName()); } } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/DumpTaskTest.java000066400000000000000000000017271451257705100254710ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.io.File; import org.apache.ant.antunit.junit3.AntUnitSuite; import org.apache.ant.antunit.junit4.AntUnitSuiteRunner; import org.junit.runner.RunWith; import junit.framework.TestSuite; @RunWith(AntUnitSuiteRunner.class) public class DumpTaskTest { public static TestSuite suite() { final File file = new File("src/org/jacoco/ant/DumpTaskTest.xml"); return new AntUnitSuite(file, DumpTaskTest.class); } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/DumpTaskTest.xml000066400000000000000000000036601451257705100253460ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/DumpTaskWithServerTest.java000066400000000000000000000021441451257705100275060ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.io.File; import org.apache.ant.antunit.junit3.AntUnitSuite; import org.apache.ant.antunit.junit4.AntUnitSuiteRunner; import org.junit.runner.RunWith; import junit.framework.TestSuite; @RunWith(AntUnitSuiteRunner.class) public class DumpTaskWithServerTest { public static TestSuite suite() { System.setProperty("org.jacoco.ant.dumpTaskWithServerTest.classes.dir", TestTarget.getClassPath()); final File file = new File( "src/org/jacoco/ant/DumpTaskWithServerTest.xml"); return new AntUnitSuite(file, DumpTaskWithServerTest.class); } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/DumpTaskWithServerTest.xml000066400000000000000000000046651451257705100273770ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/IllegalReflectiveAccessTarget.java000066400000000000000000000023301451257705100307430ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.lang.reflect.Constructor; public class IllegalReflectiveAccessTarget { public static void main(String[] args) throws Exception { try { Class.forName("java.net.UnixDomainSocketAddress"); } catch (ClassNotFoundException e) { // Java < 16 return; } final Constructor c = Class.forName("java.lang.Module") .getDeclaredConstructors()[0]; try { c.setAccessible(true); throw new AssertionError("Exception expected"); } catch (RuntimeException e) { if (!e.getClass().getName() .equals("java.lang.reflect.InaccessibleObjectException")) { throw new AssertionError( "InaccessibleObjectException expected"); } } } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/InstrumentTaskTest.java000066400000000000000000000024371451257705100267330ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.io.File; import java.io.IOException; import org.apache.ant.antunit.junit3.AntUnitSuite; import org.apache.ant.antunit.junit4.AntUnitSuiteRunner; import org.jacoco.agent.AgentJar; import org.junit.runner.RunWith; import junit.framework.TestSuite; @RunWith(AntUnitSuiteRunner.class) public class InstrumentTaskTest { public static TestSuite suite() throws IOException { System.setProperty("org.jacoco.ant.instrumentTaskTest.classes.dir", TestTarget.getClassPath()); System.setProperty("org.jacoco.ant.instrumentTaskTest.agent.file", AgentJar.extractToTempLocation().getAbsolutePath()); final File file = new File("src/org/jacoco/ant/InstrumentTaskTest.xml"); return new AntUnitSuite(file, InstrumentTaskTest.class); } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/InstrumentTaskTest.xml000066400000000000000000000136761451257705100266210ustar00rootroot00000000000000 destfile=test.exec jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/MergeTaskTest.java000066400000000000000000000017331451257705100256200ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.io.File; import org.apache.ant.antunit.junit3.AntUnitSuite; import org.apache.ant.antunit.junit4.AntUnitSuiteRunner; import org.junit.runner.RunWith; import junit.framework.TestSuite; @RunWith(AntUnitSuiteRunner.class) public class MergeTaskTest { public static TestSuite suite() { final File file = new File("src/org/jacoco/ant/MergeTaskTest.xml"); return new AntUnitSuite(file, MergeTaskTest.class); } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/MergeTaskTest.xml000066400000000000000000000046051451257705100255000ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/RemoveDebugInfos.java000066400000000000000000000025621451257705100263020ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.InputStream; import java.io.OutputStream; import org.jacoco.core.internal.InputStreams; import org.jacoco.core.internal.instr.InstrSupport; import org.objectweb.asm.ClassReader; import org.objectweb.asm.ClassWriter; /** * Test utility to remove debug information from class files. */ public class RemoveDebugInfos { public static void main(String[] args) throws Exception { final InputStream in = new FileInputStream(args[0]); final ClassReader reader = InstrSupport .classReaderFor(InputStreams.readFully(in)); in.close(); final ClassWriter writer = new ClassWriter(0); reader.accept(writer, ClassReader.SKIP_DEBUG); final OutputStream out = new FileOutputStream(args[1]); out.write(writer.toByteArray()); out.close(); } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/ReportTaskLocaleTest.java000066400000000000000000000032101451257705100271440ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import static org.junit.Assert.assertEquals; import java.util.Locale; import org.junit.Test; /** * Unit tests for the locale conversion built into {@link ReportTask}. */ public class ReportTaskLocaleTest { @Test public void testNone() { Locale locale = ReportTask.parseLocale(""); assertEquals("", locale.getLanguage()); assertEquals("", locale.getCountry()); assertEquals("", locale.getVariant()); } @Test public void testLanguage() { Locale locale = ReportTask.parseLocale("fr"); assertEquals("fr", locale.getLanguage()); assertEquals("", locale.getCountry()); assertEquals("", locale.getVariant()); } @Test public void testLanguageCountry() { Locale locale = ReportTask.parseLocale("fr_FR"); assertEquals("fr", locale.getLanguage()); assertEquals("FR", locale.getCountry()); assertEquals("", locale.getVariant()); } @Test public void testLanguageCountryVariant() { Locale locale = ReportTask.parseLocale("de_CH_Matte"); assertEquals("de", locale.getLanguage()); assertEquals("CH", locale.getCountry()); assertEquals("Matte", locale.getVariant()); } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/ReportTaskTest.java000066400000000000000000000022541451257705100260330ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.io.File; import org.apache.ant.antunit.junit3.AntUnitSuite; import org.apache.ant.antunit.junit4.AntUnitSuiteRunner; import org.junit.runner.RunWith; import junit.framework.TestSuite; @RunWith(AntUnitSuiteRunner.class) public class ReportTaskTest { public static TestSuite suite() { System.setProperty("org.jacoco.ant.reportTaskTest.classes.dir", TestTarget.getClassPath()); System.setProperty("org.jacoco.ant.reportTaskTest.sources.dir", new File("./src").getAbsolutePath()); final File file = new File("src/org/jacoco/ant/ReportTaskTest.xml"); return new AntUnitSuite(file, ReportTaskTest.class); } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/ReportTaskTest.xml000066400000000000000000000422371451257705100257170ustar00rootroot00000000000000 Source Code jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/TestTarget.java000066400000000000000000000035051451257705100251630ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.io.File; import java.io.IOException; import java.io.UnsupportedEncodingException; import java.net.URLDecoder; import org.junit.Test; /** * Simple test target for Java applications ant JUnit4 tests. To assert * execution it creates an empty file target.txt in the working * directory. */ public class TestTarget { @Test public void testNothing() throws IOException { System.out.println("Target executed"); } public static void main(String[] args) throws Exception { // Load some class from the bootstrap classloader: new java.sql.Timestamp(0); System.out.println("Target executed"); // Wait for termination file to turn up // This option puts the target in a pseudo 'server' mode if (args.length == 1) { final File termFile = new File(args[0]); while (!termFile.exists()) { Thread.sleep(100); } } } /** * @return location where this class is located */ public static String getClassPath() { final String name = TestTarget.class.getName(); final String res = "/" + name.replace('.', '/') + ".class"; String loc = TestTarget.class.getResource(res).getFile(); try { loc = URLDecoder.decode(loc, "UTF-8"); } catch (UnsupportedEncodingException e) { } return loc.substring(0, loc.length() - res.length()); } } jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/data/000077500000000000000000000000001451257705100231405ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/data/keystore.jks000066400000000000000000000043001451257705100255130ustar00rootroot00000000000000þíþítestDVVb±0‚ü0 +*‚èY4tÐ’Òàâ/•ºM5áb약‡ ™;·Ôk`PÏ‚«R¿ËU¬|·wA#KQ”…¾,}\ŒfDÊRe[69ÓÂeû’œŒJÔÒ@­‘µçW‰(ì£kÈ!ƒé­ÇQ× (¢‹Äz'õqñX¦©¸a²çË}¦ÏýDÎr ¿ui¦«Ÿ†•`™yC(Ó# Ï9&£ª&ü»¡z­^D'qQiÑ5¦,Ézì2u43<)§¸m@[´hVyXóSë.g‰€Dr»þb[©ò«o\ÙÓÆÁúÓ’_9("¬ Êͺ o°Pwfâ·©ÖÞü×WkŠ8Ÿ¤¡•ÓY 0q% ÍK¯~Sö¥–‡î.óç–æf æolÍéaÔÙ°wà,“CÔ3èa»ß²‹i.’'ì_D\Äg†ó)ÇQ^î 4œãij—tx°Š´A¨û¡­‡ù·Êãêž«[ÿ‡¼IPëÓÐ}D7„Ú¶,p°’˄ǛèOÓ§²$tãªÍضJ샡uåTãaÞ²{"Y:퀦³¦™Ï¿­v¢û¥½~¨xmùÛ”·‚²”)˜}R3ÙÈc83·§³¦ôvîá¥ÓGÀžš¾µ±ê%B6²ŒõÑ"‡Ð[VøÖD³W,K#âûñHÈký‰ÛŒ´AZ©þÿ‹çÑ‹%CTï„ßöSÛ8%Ï\Æ£µÙÑ„›»o0+É“àê;ç0ÆÖhRÍÇŠ]n(í'•wÇâ51 QÿZ¡ ÐŽ¶éˆê£T]¶|ŠKPÒf/ %hHÃãµPÆßQÃì`Böžƒ©az“)½÷do»§Y›÷€+q~±ßIÝÖÛ³* œF‰eðÃ_V×z$m£üc$4ÖUØbÝÕ¢ Í”¯‚ÿa„ßÓð;æ(„²ÛÇe)BþùäS¼r;ª¯¬s÷[n¬Åè[#WuÅjš_‘sp…^9U¬©:SšñŽbÁŽkÙU¶ÇØá_‹çºø-êD‡€Þ|~²Á+–?R?¢#*ù–ñYÜa!RvyÁÂpÌÀwˆ tÛ}Õ8!+0=Àh6_òÓ]Ì€~ô{RvÖÌ´G#¤Òÿ:[5[–Ù™ä?UŸg[@XޝY>‡à½6?nà›¹šÿ<-ûVX)…“ªCÃ!¿˜÷ö}oͤýkÖ‰ÅDé42T Ž! ŒÇr›%¶m¹K¥Ii03CfÚ&ÛM ƒ{‹jˆTƒØÚ Œün¸øð°¼Ê^œØÐÊ…(RѦu!°µça½¢µ6Mt“(ÎÔªûÓø”ž€Ä8{[ê1Љj+QòÐè;VÙŒñKjÞâ”Fä1^HQ±«²¢œÎ|ዘ*C blj‘»ïY‹DÉ^@Îj[º0w :ÀŽWþ ´/©â¥=- ÏíÁîݶùnp="ªè- «q-sŒ o‚ñfeÉn<‘Êù ¬¿nmU†ä˜ÇšÌôØt­;M5úíyÎ<<w5æŠ2„.ÍèXõ‚E*X.509{0‚w0‚_ Â\Z0  *†H†÷  0l10UUnknown10UUnknown10UUnknown10U Unknown10U Unknown10UUnknown0 140221212454Z 231231212454Z0l10UUnknown10UUnknown10UUnknown10U Unknown10U Unknown10UUnknown0‚"0  *†H†÷ ‚0‚ ‚©ªŒËÊvê3÷“´ýnEòâ¬Â×§«tÁe𴦥[ï’¾V顤Sœþ•Ð1åp žü¡Ä9"‘ZÎ}Xਗw=Å7ôx}”šŸ œ`ï*ÁÕÿÛ‚t¥¢è\±¤_:Ñ –D°’Î/%óºl‘EU+3À‘Ýp%í’΂>Ù2z!—©E=€¨ƒšÁF(»¨ò¡GÌöcÆN<¢ž<5ò–G%5/~lÐˤB5)*.VRÈUŒÂÚ‹Ö󲎒ƒO›*¸Õê*ixý×øêŸvX94sMZñ×}o°d݈nœGMI ¯R̨è«Ù’sq;£!00U%"O ƒ:aØh9ÛB¿¦j%x0  *†H†÷  ‚‹ÌXÉ+ ì‘Ü!hmËV_ú1‹>¯6ŒÙåðpN8\ úÿaBخɹ;m¥’ŬGº P(”ñLBº@)&L-oS¸¦!N~#«f…—oÝsml¦ŽÚúóBd¼ºFr¨S »ÉŒ©‰ÿî^ßÊ—o.Æ+dû`ÂxI`[O ´)åáãðRÿ¼…ÿ¤†!æå[ ÿTOò–Gvþ3M» ”°6Õ·ÕjK!bMzeH/6ßž›‚—õâY“ìZ†§6Vx€½áF, ÙÅi®YDËE‡uf,·-‘ÔîvÖ©ñð[ ƒ¼Å¤ÐìLÊKÃU¡€³Rz]²Í¨þ7ûANÒé=«œ›ï^-^¦‡RÏjacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/data/nomatch.exec000066400000000000000000000000521451257705100254340ustar00rootroot00000000000000ÀÀorg/jacoco/ant/TestTargetjacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/data/policy.txt000066400000000000000000000007621451257705100252050ustar00rootroot00000000000000grant codeBase "file:${jacoco.agent}" { permission java.io.FilePermission "${jacoco.exec}/..", "read"; permission java.io.FilePermission "${jacoco.exec}", "write"; permission java.lang.RuntimePermission "shutdownHooks"; permission java.lang.RuntimePermission "createClassLoader"; permission java.lang.RuntimePermission "getProtectionDomain"; permission java.lang.reflect.ReflectPermission "suppressAccessChecks"; permission java.lang.RuntimePermission "defineClass"; }; jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/data/sample.bad000066400000000000000000000000151451257705100250650ustar00rootroot00000000000000No exec file.jacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/data/sample1.exec000066400000000000000000000000051451257705100253430ustar00rootroot00000000000000ÀÀjacoco-0.8.11/org.jacoco.ant.test/src/org/jacoco/ant/data/sample2.exec000066400000000000000000000000051451257705100253440ustar00rootroot00000000000000ÀÀjacoco-0.8.11/org.jacoco.ant/000077500000000000000000000000001451257705100156535ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.ant/.classpath000066400000000000000000000014151451257705100176370ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.ant/.project000066400000000000000000000013601451257705100173220ustar00rootroot00000000000000 org.jacoco.ant org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core/.settings jacoco-0.8.11/org.jacoco.ant/about.html000066400000000000000000000017601451257705100176570ustar00rootroot00000000000000 About

About This Content

${build.date}

License

All Content in this distribution is made available by Mountainminds GmbH & Co. KG, Munich. Unless otherwise indicated below, the Content is provided to you under the terms and conditions of the Eclipse Public License Version 2.0 ("EPL"). A copy of the EPL is available at https://www.eclipse.org/legal/epl-2.0/. For purposes of the EPL, "Program" will mean the Content.

Third Party Content

The Content includes items that have been sourced from third parties as set out below.

${asm.license} ${googlecodeprettify.license} jacoco-0.8.11/org.jacoco.ant/pom.xml000066400000000000000000000103041451257705100171660ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.build 0.8.11 ../org.jacoco.build org.jacoco.ant JaCoCo :: Ant JaCoCo Ant Tasks ${project.groupId} org.jacoco.core ${project.groupId} org.jacoco.report ${project.groupId} org.jacoco.agent org.apache.ant ant provided src org.apache.maven.plugins maven-shade-plugin package shade true nodeps true org.objectweb.asm org.jacoco.asm org.ow2.asm:* module-info.class ${project.description} ${project.organization.name} ${project.version} org.apache.felix maven-bundle-plugin package bundle true org.apache.ant;bundle-version="[1.7.0,2.0.0)" jacoco-0.8.11/org.jacoco.ant/src/000077500000000000000000000000001451257705100164425ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.ant/src/org/000077500000000000000000000000001451257705100172315ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.ant/src/org/jacoco/000077500000000000000000000000001451257705100204675ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.ant/src/org/jacoco/ant/000077500000000000000000000000001451257705100212515ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.ant/src/org/jacoco/ant/AbstractCoverageTask.java000066400000000000000000000145751451257705100261720ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.io.File; import java.io.IOException; import org.apache.tools.ant.BuildException; import org.apache.tools.ant.Task; import org.jacoco.agent.AgentJar; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.runtime.AgentOptions.OutputMode; /** * Base class for all coverage tasks that require agent options */ public class AbstractCoverageTask extends Task { private final AgentOptions agentOptions; private File destfile; private boolean enabled; /** * Create default agent options */ protected AbstractCoverageTask() { super(); agentOptions = new AgentOptions(); destfile = new File(AgentOptions.DEFAULT_DESTFILE); enabled = true; } /** * @return Whether or not the current task is enabled */ public boolean isEnabled() { return enabled; } /** * Sets whether or not the current task is enabled * * @param enabled * Enablement state of the task */ public void setEnabled(final boolean enabled) { this.enabled = enabled; } /** * Sets the location to write coverage execution data to. Default is * jacoco.exec. * * @param file * Location to write coverage execution data to */ public void setDestfile(final File file) { destfile = file; } /** * Append execution coverage data if a coverage file is already present. * Default is true * * @param append * true to append execution data to an existing file */ public void setAppend(final boolean append) { agentOptions.setAppend(append); } /** * List of wildcard patterns classes to include for instrumentation. Default * is * * * @param includes * Wildcard pattern of included classes */ public void setIncludes(final String includes) { agentOptions.setIncludes(includes); } /** * List of wildcard patterns classes to exclude from instrumentation. * Default is the empty string, no classes excluded * * @param excludes * Wildcard pattern of excluded classes */ public void setExcludes(final String excludes) { agentOptions.setExcludes(excludes); } /** * List of wildcard patterns for classloaders that JaCoCo will not * instrument classes from. Default is * sun.reflect.DelegatingClassLoader * * @param exclClassLoader * Wildcard pattern of class loaders to exclude */ public void setExclClassLoader(final String exclClassLoader) { agentOptions.setExclClassloader(exclClassLoader); } /** * Sets whether classes from the bootstrap classloader should be * instrumented. * * @param include * true if bootstrap classes should be instrumented */ public void setInclBootstrapClasses(final boolean include) { agentOptions.setInclBootstrapClasses(include); } /** * Sets whether classes without source location should be instrumented. * * @param include * true if classes without source location should be * instrumented */ public void setInclNoLocationClasses(final boolean include) { agentOptions.setInclNoLocationClasses(include); } /** * Sets the session identifier. Default is a auto-generated id * * @param id * session identifier */ public void setSessionId(final String id) { agentOptions.setSessionId(id); } /** * Dump coverage data on VM termination. Default is true * * @param dumpOnExit * true to write coverage data on VM termination */ public void setDumpOnExit(final boolean dumpOnExit) { agentOptions.setDumpOnExit(dumpOnExit); } /** * Sets the output method. Default is file * * @param output * Output method */ public void setOutput(final String output) { agentOptions.setOutput(output); } /** * Sets the IP address or hostname to bind to when output method is tcp * server or connect to when the output method is tcp client. Default is * localhost * * @param address * Address to bind or connect to */ public void setAddress(final String address) { agentOptions.setAddress(address); } /** * Sets the Port to bind to when the output method is tcp server or connect * to when the output method is tcp client. Default is 6300 * * @param port * port to bind to or connect to */ public void setPort(final int port) { agentOptions.setPort(port); } /** * Sets the directory where all class files seen by the agent should be * dumped to. * * @param dir * dump output location */ public void setClassdumpdir(final File dir) { agentOptions.setClassDumpDir(dir.getAbsolutePath()); } /** * Sets whether the agent should expose functionality via JMX. * * @param jmx * true if JMX should be enabled */ public void setJmx(final boolean jmx) { agentOptions.setJmx(jmx); } /** * Creates JVM argument to launch with the specified JaCoCo agent jar and * the current options * * @return JVM Argument to pass to new VM */ protected String getLaunchingArgument() { return prepareAgentOptions().getVMArgument(getAgentFile()); } private AgentOptions prepareAgentOptions() { if (OutputMode.file.equals(agentOptions.getOutput())) { agentOptions.setDestfile(destfile.getAbsolutePath()); } return agentOptions; } private File getAgentFile() { try { File agentFile = null; final String agentFileLocation = getProject() .getProperty("_jacoco.agentFile"); if (agentFileLocation != null) { agentFile = new File(agentFileLocation); } else { agentFile = AgentJar.extractToTempLocation(); getProject().setProperty("_jacoco.agentFile", agentFile.toString()); } return agentFile; } catch (final IOException e) { throw new BuildException("Unable to extract agent jar", e, getLocation()); } } } jacoco-0.8.11/org.jacoco.ant/src/org/jacoco/ant/AgentTask.java000066400000000000000000000031251451257705100237760ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import org.apache.tools.ant.BuildException; /** * Ant task that will unpack the coverage agent jar and generate the JVM options * required to use it */ public class AgentTask extends AbstractCoverageTask { private String property; /** * Sets the name of the property to hold the agent JVM options * * @param property * Name of the property to be populated */ public void setProperty(final String property) { this.property = property; } /** * Unpacks a private copy of the JaCoCo agent and populates * property with the JVM arguments required to use it. The * value set into the property is only valid for the lifetime of the current * JVM. The agent jar will be removed on termination of the JVM. */ @Override public void execute() throws BuildException { if (property == null || property.length() == 0) { throw new BuildException("Property is mandatory", getLocation()); } final String jvmArg = isEnabled() ? getLaunchingArgument() : ""; getProject().setNewProperty(property, jvmArg); } } jacoco-0.8.11/org.jacoco.ant/src/org/jacoco/ant/AntFilesLocator.java000066400000000000000000000030441451257705100251460ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import java.io.File; import java.io.IOException; import java.io.InputStream; import java.util.HashMap; import java.util.Map; import org.apache.tools.ant.types.Resource; import org.jacoco.report.InputStreamSourceFileLocator; /** * Source locator based on Ant file resources. */ class AntFilesLocator extends InputStreamSourceFileLocator { private final Map resources; public AntFilesLocator(final String encoding, final int tabWidth) { super(encoding, tabWidth); this.resources = new HashMap(); } /** * Adds the given file resource as a potential source file. * * @param file * file resource to add */ void add(final Resource file) { resources.put(file.getName().replace(File.separatorChar, '/'), file); } @Override protected InputStream getSourceStream(final String path) throws IOException { final Resource file = resources.get(path); if (file == null) { return null; } else { return file.getInputStream(); } } } jacoco-0.8.11/org.jacoco.ant/src/org/jacoco/ant/AntResourcesLocator.java000066400000000000000000000044421451257705100260610ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * Dominik Stadler - source folder support * *******************************************************************************/ package org.jacoco.ant; import java.util.Iterator; import org.apache.tools.ant.types.Resource; import org.apache.tools.ant.types.resources.FileResource; import org.jacoco.report.DirectorySourceFileLocator; import org.jacoco.report.MultiSourceFileLocator; /** * Source file locator based on Ant resources. The locator supports files as * well as directories. The lookup is first performed on files (matching the * local file name) and afterwards on directories, by the order the directory * resources have been added. The directories are considered as source folders * that are searched for source files with the fully qualified name (package and * local name). */ class AntResourcesLocator extends MultiSourceFileLocator { private final String encoding; private final AntFilesLocator filesLocator; private boolean empty; AntResourcesLocator(final String encoding, final int tabWidth) { super(tabWidth); this.encoding = encoding; this.filesLocator = new AntFilesLocator(encoding, tabWidth); this.empty = true; super.add(filesLocator); } /** * Adds the given file or directory resource to the locator. * * @param resource * resource to add */ void add(final Resource resource) { empty = false; if (resource.isDirectory()) { final FileResource dir = (FileResource) resource; super.add(new DirectorySourceFileLocator(dir.getFile(), encoding, getTabWidth())); } else { filesLocator.add(resource); } } void addAll(final Iterator iterator) { while (iterator.hasNext()) { add((Resource) iterator.next()); } } /** * Checks, whether resources have been added. * * @return true, if no resources have been added */ boolean isEmpty() { return empty; } } jacoco-0.8.11/org.jacoco.ant/src/org/jacoco/ant/CoverageTask.java000066400000000000000000000130221451257705100244700ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - TestNG support * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import static java.lang.String.format; import java.util.ArrayList; import java.util.Collection; import org.apache.tools.ant.BuildException; import org.apache.tools.ant.Project; import org.apache.tools.ant.RuntimeConfigurable; import org.apache.tools.ant.Task; import org.apache.tools.ant.TaskContainer; import org.apache.tools.ant.UnknownElement; /** * Container task to run Java/JUnit tasks with the JaCoCo agent jar. Coverage * will only be applied if all of the following are true: *
    *
  • Exactly one sub task may be present
  • *
  • Task must be either Java or JUnit
  • *
  • Task must be using a forked VM (so vm args can be passed)
  • *
*/ public class CoverageTask extends AbstractCoverageTask implements TaskContainer { private final Collection taskEnhancers = new ArrayList(); private Task childTask; /** * Creates a new default coverage task */ public CoverageTask() { super(); taskEnhancers.add(new JavaLikeTaskEnhancer("java")); taskEnhancers.add(new JavaLikeTaskEnhancer("junit")); taskEnhancers.add(new TestNGTaskEnhancer("testng")); } /** * Add child task to this container and reconfigure it to run with coverage * enabled */ public void addTask(final Task task) { if (childTask != null) { throw new BuildException( "Only one child task can be supplied to the coverge task", getLocation()); } this.childTask = task; final String subTaskTypeName = task.getTaskType(); final TaskEnhancer enhancer = findEnhancerForTask(subTaskTypeName); if (enhancer == null) { throw new BuildException( format("%s is not a valid child of the coverage task", subTaskTypeName), getLocation()); } if (isEnabled()) { log(format("Enhancing %s with coverage", childTask.getTaskName())); enhancer.enhanceTask(task); } task.maybeConfigure(); } private TaskEnhancer findEnhancerForTask(final String taskName) { for (final TaskEnhancer enhancer : taskEnhancers) { if (enhancer.supportsTask(taskName)) { return enhancer; } } return null; } /** * Executes subtask and performs any required cleanup */ @Override public void execute() throws BuildException { if (childTask == null) { throw new BuildException( "A child task must be supplied for the coverage task", getLocation()); } childTask.execute(); } /** * Task enhancer for TestNG. TestNG task always run in a forked VM and has * nested jvmargs elements */ private class TestNGTaskEnhancer extends JavaLikeTaskEnhancer { public TestNGTaskEnhancer(final String supportedTaskName) { super(supportedTaskName); } @Override public void enhanceTask(final Task task) { addJvmArgs(task); } } /** * Basic task enhancer that can handle all 'java like' tasks. That is, tasks * that have a top level fork attribute and nested jvmargs elements */ private class JavaLikeTaskEnhancer implements TaskEnhancer { private final String supportedTaskName; public JavaLikeTaskEnhancer(final String supportedTaskName) { this.supportedTaskName = supportedTaskName; } public boolean supportsTask(final String taskname) { return taskname.equals(supportedTaskName); } public void enhanceTask(final Task task) { final RuntimeConfigurable configurableWrapper = task .getRuntimeConfigurableWrapper(); final String forkValue = getProject().replaceProperties( (String) configurableWrapper.getAttributeMap().get("fork")); if (!Project.toBoolean(forkValue)) { throw new BuildException( "Coverage can only be applied on a forked VM", getLocation()); } addJvmArgs(task); } public void addJvmArgs(final Task task) { final UnknownElement el = new UnknownElement("jvmarg"); el.setTaskName("jvmarg"); el.setQName("jvmarg"); final RuntimeConfigurable runtimeConfigurableWrapper = el .getRuntimeConfigurableWrapper(); runtimeConfigurableWrapper.setAttribute("value", getLaunchingArgument()); task.getRuntimeConfigurableWrapper() .addChild(runtimeConfigurableWrapper); ((UnknownElement) task).addChild(el); } } /** * The task enhancer is responsible for potentially reconfiguring a task to * support running with code coverage enabled */ private interface TaskEnhancer { /** * @param taskname * Task type to enhance * @return true if this enhancer is capable of enhancing * the requested task type */ boolean supportsTask(String taskname); /** * Attempt to enhance the supplied task with coverage information. This * operation may fail if the task is being executed in the current VM * * @param task * Task instance to enhance (usually an * {@link UnknownElement}) * @throws BuildException * Thrown if this enhancer can handle this type of task, but * this instance can not be enhanced for some reason. */ void enhanceTask(Task task) throws BuildException; } } jacoco-0.8.11/org.jacoco.ant/src/org/jacoco/ant/DumpTask.java000066400000000000000000000103361451257705100236470ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import static java.lang.String.format; import java.io.File; import java.io.IOException; import java.net.InetAddress; import org.apache.tools.ant.BuildException; import org.apache.tools.ant.Task; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.tools.ExecDumpClient; import org.jacoco.core.tools.ExecFileLoader; /** * Ant task for remotely controlling an application that is running with the * tcpserver output mode */ public class DumpTask extends Task { private boolean dump = true; private boolean reset = false; private File destfile = null; private String address = AgentOptions.DEFAULT_ADDRESS; private int port = AgentOptions.DEFAULT_PORT; private int retryCount = 10; private boolean append = true; /** * Sets the location of the execution data file to write. This parameter is * required when dump is true. Default is * jacoco.exec * * @param destfile * Location to write execution data to */ public void setDestfile(final File destfile) { this.destfile = destfile; } /** * IP Address or hostname to connect to. Defaults to localhost * * @param address * IP Address or hostname to connect to */ public void setAddress(final String address) { this.address = address; } /** * Port number to connect to. Default is 6300 * * @param port * Port to connect to */ public void setPort(final int port) { this.port = port; } /** * Number of retries which the goal will attempt to establish a connection. * This can be used to wait until the target JVM is successfully launched. * * @param retryCount * number of retries */ public void setRetryCount(final int retryCount) { this.retryCount = retryCount; } /** * true if the destination file it to be appended to. * false if the file is to be overwritten * * @param append * true if the destination file should be appended * to */ public void setAppend(final boolean append) { this.append = append; } /** * Sets whether execution data should be downloaded from the remote host. * Defaults to true * * @param dump * true to download execution data */ public void setDump(final boolean dump) { this.dump = dump; } /** * Sets whether a reset command should be sent after the execution data has * been dumped. Defaults to false * * @param reset * true to reset execution data */ public void setReset(final boolean reset) { this.reset = reset; } @Override public void execute() throws BuildException { if (port <= 0) { throw new BuildException("Invalid port value", getLocation()); } if (dump && destfile == null) { throw new BuildException( "Destination file is required when dumping execution data", getLocation()); } final ExecDumpClient client = new ExecDumpClient() { @Override protected void onConnecting(final InetAddress address, final int port) { log(format("Connecting to %s:%s", address, Integer.valueOf(port))); } @Override protected void onConnectionFailure(final IOException exception) { log(exception.getMessage()); } }; client.setDump(dump); client.setReset(reset); client.setRetryCount(retryCount); try { final ExecFileLoader loader = client.dump(address, port); if (dump) { log(format("Dumping execution data to %s", destfile.getAbsolutePath())); loader.save(destfile, append); } } catch (final IOException e) { throw new BuildException("Unable to dump coverage data", e, getLocation()); } } } jacoco-0.8.11/org.jacoco.ant/src/org/jacoco/ant/InstrumentTask.java000066400000000000000000000065721451257705100251210ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import static java.lang.String.format; import java.io.File; import java.io.FileOutputStream; import java.io.InputStream; import java.io.OutputStream; import java.util.Iterator; import org.apache.tools.ant.BuildException; import org.apache.tools.ant.Task; import org.apache.tools.ant.types.Resource; import org.apache.tools.ant.types.ResourceCollection; import org.apache.tools.ant.types.resources.Union; import org.apache.tools.ant.util.FileUtils; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.runtime.OfflineInstrumentationAccessGenerator; /** * Task for offline instrumentation of class files. */ public class InstrumentTask extends Task { private File destdir; private final Union files = new Union(); private boolean removesignatures = true; /** * Sets the location of the instrumented classes. * * @param destdir * destination folder for instrumented classes */ public void setDestdir(final File destdir) { this.destdir = destdir; } /** * Sets whether signatures should be removed from JAR files. * * @param removesignatures * true if signatures should be removed */ public void setRemovesignatures(final boolean removesignatures) { this.removesignatures = removesignatures; } /** * This task accepts any number of class file resources. * * @param resources * Execution data resources */ public void addConfigured(final ResourceCollection resources) { files.add(resources); } @Override public void execute() throws BuildException { if (destdir == null) { throw new BuildException("Destination directory must be supplied", getLocation()); } int total = 0; final Instrumenter instrumenter = new Instrumenter( new OfflineInstrumentationAccessGenerator()); instrumenter.setRemoveSignatures(removesignatures); final Iterator resourceIterator = files.iterator(); while (resourceIterator.hasNext()) { final Resource resource = (Resource) resourceIterator.next(); if (resource.isDirectory()) { continue; } total += instrument(instrumenter, resource); } log(format("Instrumented %s classes to %s", Integer.valueOf(total), destdir.getAbsolutePath())); } private int instrument(final Instrumenter instrumenter, final Resource resource) { final File file = new File(destdir, resource.getName()); file.getParentFile().mkdirs(); try { InputStream input = null; OutputStream output = null; try { input = resource.getInputStream(); output = new FileOutputStream(file); return instrumenter.instrumentAll(input, output, resource.getName()); } finally { FileUtils.close(input); FileUtils.close(output); } } catch (final Exception e) { file.delete(); throw new BuildException( format("Error while instrumenting %s", resource), e, getLocation()); } } } jacoco-0.8.11/org.jacoco.ant/src/org/jacoco/ant/MergeTask.java000066400000000000000000000055331451257705100240040ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Brock Janiczak - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import static java.lang.String.format; import java.io.File; import java.io.IOException; import java.io.InputStream; import java.util.Iterator; import org.apache.tools.ant.BuildException; import org.apache.tools.ant.Task; import org.apache.tools.ant.types.Resource; import org.apache.tools.ant.types.ResourceCollection; import org.apache.tools.ant.types.resources.Union; import org.apache.tools.ant.util.FileUtils; import org.jacoco.core.tools.ExecFileLoader; /** * Task for merging a set of execution data files (*.exec) into a single file */ public class MergeTask extends Task { private File destfile; private final Union files = new Union(); /** * Sets the location of the merged data store * * @param destfile * Destination data store location */ public void setDestfile(final File destfile) { this.destfile = destfile; } /** * This task accepts any number of execution data resources. * * @param resources * Execution data resources */ public void addConfigured(final ResourceCollection resources) { files.add(resources); } @Override public void execute() throws BuildException { if (destfile == null) { throw new BuildException("Destination file must be supplied", getLocation()); } final ExecFileLoader loader = new ExecFileLoader(); load(loader); save(loader); } private void load(final ExecFileLoader loader) { final Iterator resourceIterator = files.iterator(); while (resourceIterator.hasNext()) { final Resource resource = (Resource) resourceIterator.next(); if (resource.isDirectory()) { continue; } log(format("Loading execution data file %s", resource)); InputStream resourceStream = null; try { resourceStream = resource.getInputStream(); loader.load(resourceStream); } catch (final IOException e) { throw new BuildException(format("Unable to read %s", resource), e, getLocation()); } finally { FileUtils.close(resourceStream); } } } private void save(final ExecFileLoader loader) { log(format("Writing merged execution data to %s", destfile.getAbsolutePath())); try { loader.save(destfile, false); } catch (final IOException e) { throw new BuildException(format("Unable to write merged file %s", destfile.getAbsolutePath()), e, getLocation()); } } } jacoco-0.8.11/org.jacoco.ant/src/org/jacoco/ant/ReportTask.java000066400000000000000000000405151451257705100242170ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.ant; import static java.lang.String.format; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.util.ArrayList; import java.util.Collection; import java.util.Iterator; import java.util.List; import java.util.Locale; import java.util.StringTokenizer; import org.apache.tools.ant.BuildException; import org.apache.tools.ant.Project; import org.apache.tools.ant.Task; import org.apache.tools.ant.types.Resource; import org.apache.tools.ant.types.resources.FileResource; import org.apache.tools.ant.types.resources.Union; import org.apache.tools.ant.util.FileUtils; import org.jacoco.core.analysis.Analyzer; import org.jacoco.core.analysis.CoverageBuilder; import org.jacoco.core.analysis.IBundleCoverage; import org.jacoco.core.analysis.IClassCoverage; import org.jacoco.core.analysis.ICoverageNode; import org.jacoco.core.data.ExecutionDataStore; import org.jacoco.core.data.SessionInfoStore; import org.jacoco.core.tools.ExecFileLoader; import org.jacoco.report.FileMultiReportOutput; import org.jacoco.report.IMultiReportOutput; import org.jacoco.report.IReportGroupVisitor; import org.jacoco.report.IReportVisitor; import org.jacoco.report.MultiReportVisitor; import org.jacoco.report.ZipMultiReportOutput; import org.jacoco.report.check.IViolationsOutput; import org.jacoco.report.check.Limit; import org.jacoco.report.check.Rule; import org.jacoco.report.check.RulesChecker; import org.jacoco.report.csv.CSVFormatter; import org.jacoco.report.html.HTMLFormatter; import org.jacoco.report.xml.XMLFormatter; /** * Task for coverage report generation. */ public class ReportTask extends Task { /** * The source files are specified in a resource collection with additional * attributes. */ public static class SourceFilesElement extends Union { String encoding = null; int tabWidth = 4; /** * Defines the optional source file encoding. If not set the platform * default is used. * * @param encoding * source file encoding */ public void setEncoding(final String encoding) { this.encoding = encoding; } /** * Sets the tab stop width for the source pages. Default value is 4. * * @param tabWidth * number of characters per tab stop */ public void setTabwidth(final int tabWidth) { if (tabWidth <= 0) { throw new BuildException("Tab width must be greater than 0"); } this.tabWidth = tabWidth; } } /** * Container element for class file groups. */ public static class GroupElement { private final List children = new ArrayList(); private final Union classfiles = new Union(); private final SourceFilesElement sourcefiles = new SourceFilesElement(); private String name; /** * Sets the name of the group. * * @param name * name of the group */ public void setName(final String name) { this.name = name; } /** * Creates a new child group. * * @return new child group */ public GroupElement createGroup() { final GroupElement group = new GroupElement(); children.add(group); return group; } /** * Returns the nested resource collection for class files. * * @return resource collection for class files */ public Union createClassfiles() { return classfiles; } /** * Returns the nested resource collection for source files. * * @return resource collection for source files */ public SourceFilesElement createSourcefiles() { return sourcefiles; } } /** * Interface for child elements that define formatters. */ private abstract class FormatterElement { abstract IReportVisitor createVisitor() throws IOException; void finish() { } } /** * Formatter element for HTML reports. */ public class HTMLFormatterElement extends FormatterElement { private File destdir; private File destfile; private String footer = ""; private String encoding = "UTF-8"; private Locale locale = Locale.getDefault(); /** * Sets the output directory for the report. * * @param destdir * output directory */ public void setDestdir(final File destdir) { this.destdir = destdir; } /** * Sets the Zip output file for the report. * * @param destfile * Zip output file */ public void setDestfile(final File destfile) { this.destfile = destfile; } /** * Sets an optional footer text that will be displayed on every report * page. * * @param text * footer text */ public void setFooter(final String text) { this.footer = text; } /** * Sets the output encoding for generated HTML files. Default is UTF-8. * * @param encoding * output encoding */ public void setEncoding(final String encoding) { this.encoding = encoding; } /** * Sets the locale for generated text output. By default the platform * locale is used. * * @param locale * text locale */ public void setLocale(final String locale) { this.locale = parseLocale(locale); } @Override public IReportVisitor createVisitor() throws IOException { final IMultiReportOutput output; if (destfile != null) { if (destdir != null) { throw new BuildException( "Either destination directory or file must be supplied, not both", getLocation()); } final FileOutputStream stream = new FileOutputStream(destfile); output = new ZipMultiReportOutput(stream); } else { if (destdir == null) { throw new BuildException( "Destination directory or file must be supplied for html report", getLocation()); } output = new FileMultiReportOutput(destdir); } final HTMLFormatter formatter = new HTMLFormatter(); formatter.setFooterText(footer); formatter.setOutputEncoding(encoding); formatter.setLocale(locale); return formatter.createVisitor(output); } } /** * Formatter element for CSV reports. */ public class CSVFormatterElement extends FormatterElement { private File destfile; private String encoding = "UTF-8"; /** * Sets the output file for the report. * * @param destfile * output file */ public void setDestfile(final File destfile) { this.destfile = destfile; } @Override public IReportVisitor createVisitor() throws IOException { if (destfile == null) { throw new BuildException( "Destination file must be supplied for csv report", getLocation()); } final CSVFormatter formatter = new CSVFormatter(); formatter.setOutputEncoding(encoding); return formatter.createVisitor(new FileOutputStream(destfile)); } /** * Sets the output encoding for generated XML file. Default is UTF-8. * * @param encoding * output encoding */ public void setEncoding(final String encoding) { this.encoding = encoding; } } /** * Formatter element for XML reports. */ public class XMLFormatterElement extends FormatterElement { private File destfile; private String encoding = "UTF-8"; /** * Sets the output file for the report. * * @param destfile * output file */ public void setDestfile(final File destfile) { this.destfile = destfile; } /** * Sets the output encoding for generated XML file. Default is UTF-8. * * @param encoding * output encoding */ public void setEncoding(final String encoding) { this.encoding = encoding; } @Override public IReportVisitor createVisitor() throws IOException { if (destfile == null) { throw new BuildException( "Destination file must be supplied for xml report", getLocation()); } final XMLFormatter formatter = new XMLFormatter(); formatter.setOutputEncoding(encoding); return formatter.createVisitor(new FileOutputStream(destfile)); } } /** * Formatter element for coverage checks. */ public class CheckFormatterElement extends FormatterElement implements IViolationsOutput { private final List rules = new ArrayList(); private boolean violations = false; private boolean failOnViolation = true; private String violationsPropery = null; /** * Creates and adds a new rule. * * @return new rule */ public Rule createRule() { final Rule rule = new Rule(); rules.add(rule); return rule; } /** * Sets whether the build should fail in case of a violation. Default is * true. * * @param flag * if true the build fails on violation */ public void setFailOnViolation(final boolean flag) { this.failOnViolation = flag; } /** * Sets the name of a property to append the violation messages to. * * @param property * name of a property */ public void setViolationsProperty(final String property) { this.violationsPropery = property; } @Override public IReportVisitor createVisitor() throws IOException { final RulesChecker formatter = new RulesChecker(); formatter.setRules(rules); return formatter.createVisitor(this); } public void onViolation(final ICoverageNode node, final Rule rule, final Limit limit, final String message) { log(message, Project.MSG_ERR); violations = true; if (violationsPropery != null) { final String old = getProject().getProperty(violationsPropery); final String value = old == null ? message : String.format("%s\n%s", old, message); getProject().setProperty(violationsPropery, value); } } @Override void finish() { if (violations && failOnViolation) { throw new BuildException( "Coverage check failed due to violated rules.", getLocation()); } } } private final Union executiondataElement = new Union(); private SessionInfoStore sessionInfoStore; private ExecutionDataStore executionDataStore; private final GroupElement structure = new GroupElement(); private final List formatters = new ArrayList(); /** * Returns the nested resource collection for execution data files. * * @return resource collection for execution files */ public Union createExecutiondata() { return executiondataElement; } /** * Returns the root group element that defines the report structure. * * @return root group element */ public GroupElement createStructure() { return structure; } /** * Creates a new HTML report element. * * @return HTML report element */ public HTMLFormatterElement createHtml() { final HTMLFormatterElement element = new HTMLFormatterElement(); formatters.add(element); return element; } /** * Creates a new CSV report element. * * @return CSV report element */ public CSVFormatterElement createCsv() { final CSVFormatterElement element = new CSVFormatterElement(); formatters.add(element); return element; } /** * Creates a new coverage check element. * * @return coverage check element */ public CheckFormatterElement createCheck() { final CheckFormatterElement element = new CheckFormatterElement(); formatters.add(element); return element; } /** * Creates a new XML report element. * * @return CSV report element */ public XMLFormatterElement createXml() { final XMLFormatterElement element = new XMLFormatterElement(); formatters.add(element); return element; } @Override public void execute() throws BuildException { loadExecutionData(); try { final IReportVisitor visitor = createVisitor(); visitor.visitInfo(sessionInfoStore.getInfos(), executionDataStore.getContents()); createReport(visitor, structure); visitor.visitEnd(); for (final FormatterElement f : formatters) { f.finish(); } } catch (final IOException e) { throw new BuildException("Error while creating report", e, getLocation()); } } private void loadExecutionData() { final ExecFileLoader loader = new ExecFileLoader(); for (final Iterator i = executiondataElement.iterator(); i .hasNext();) { final Resource resource = (Resource) i.next(); log(format("Loading execution data file %s", resource)); InputStream in = null; try { in = resource.getInputStream(); loader.load(in); } catch (final IOException e) { throw new BuildException( format("Unable to read execution data file %s", resource), e, getLocation()); } finally { FileUtils.close(in); } } sessionInfoStore = loader.getSessionInfoStore(); executionDataStore = loader.getExecutionDataStore(); } private IReportVisitor createVisitor() throws IOException { final List visitors = new ArrayList(); for (final FormatterElement f : formatters) { visitors.add(f.createVisitor()); } return new MultiReportVisitor(visitors); } private void createReport(final IReportGroupVisitor visitor, final GroupElement group) throws IOException { if (group.name == null) { throw new BuildException("Group name must be supplied", getLocation()); } if (group.children.isEmpty()) { final IBundleCoverage bundle = createBundle(group); final SourceFilesElement sourcefiles = group.sourcefiles; final AntResourcesLocator locator = new AntResourcesLocator( sourcefiles.encoding, sourcefiles.tabWidth); locator.addAll(sourcefiles.iterator()); if (!locator.isEmpty()) { checkForMissingDebugInformation(bundle); } visitor.visitBundle(bundle, locator); } else { final IReportGroupVisitor groupVisitor = visitor .visitGroup(group.name); for (final GroupElement child : group.children) { createReport(groupVisitor, child); } } } private IBundleCoverage createBundle(final GroupElement group) throws IOException { final CoverageBuilder builder = new CoverageBuilder(); final Analyzer analyzer = new Analyzer(executionDataStore, builder); for (final Iterator i = group.classfiles.iterator(); i.hasNext();) { final Resource resource = (Resource) i.next(); if (resource.isDirectory() && resource instanceof FileResource) { analyzer.analyzeAll(((FileResource) resource).getFile()); } else { final InputStream in = resource.getInputStream(); analyzer.analyzeAll(in, resource.getName()); in.close(); } } final IBundleCoverage bundle = builder.getBundle(group.name); logBundleInfo(bundle, builder.getNoMatchClasses()); return bundle; } private void logBundleInfo(final IBundleCoverage bundle, final Collection nomatch) { log(format("Writing bundle '%s' with %s classes", bundle.getName(), Integer.valueOf(bundle.getClassCounter().getTotalCount()))); if (!nomatch.isEmpty()) { log(format( "Classes in bundle '%s' do not match with execution data. " + "For report generation the same class files must be used as at runtime.", bundle.getName()), Project.MSG_WARN); for (final IClassCoverage c : nomatch) { log(format("Execution data for class %s does not match.", c.getName()), Project.MSG_WARN); } } } private void checkForMissingDebugInformation(final ICoverageNode node) { if (node.containsCode() && node.getLineCounter().getTotalCount() == 0) { log(format( "To enable source code annotation class files for bundle '%s' have to be compiled with debug information.", node.getName()), Project.MSG_WARN); } } /** * Splits a given underscore "_" separated string and creates a Locale. This * method is implemented as the method Locale.forLanguageTag() was not * available in Java 5. * * @param locale * String representation of a Locate * @return Locale instance */ static Locale parseLocale(final String locale) { final StringTokenizer st = new StringTokenizer(locale, "_"); final String language = st.hasMoreTokens() ? st.nextToken() : ""; final String country = st.hasMoreTokens() ? st.nextToken() : ""; final String variant = st.hasMoreTokens() ? st.nextToken() : ""; return new Locale(language, country, variant); } } jacoco-0.8.11/org.jacoco.ant/src/org/jacoco/ant/antlib.xml000066400000000000000000000014571451257705100232530ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.build/000077500000000000000000000000001451257705100161705ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.build/.project000066400000000000000000000007161451257705100176430ustar00rootroot00000000000000 org.jacoco.build org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature jacoco-0.8.11/org.jacoco.build/licenses/000077500000000000000000000000001451257705100177755ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.build/licenses/args4j-2.0.28.html000066400000000000000000000023401451257705100226010ustar00rootroot00000000000000

args4j

args4j 2.0.28 is subject to the terms and conditions of the following license:

Copyright (c) 2013 Kohsuke Kawaguchi and other contributors

Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
jacoco-0.8.11/org.jacoco.build/licenses/asm-9.6.html000066400000000000000000000032701451257705100217570ustar00rootroot00000000000000

ASM

ASM 9.6 is subject to the terms and conditions of the following license:

ASM: a very small and fast Java bytecode manipulation framework
Copyright (c) 2000-2011 INRIA, France Telecom
All rights reserved.

Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions
are met:
1. Redistributions of source code must retain the above copyright
   notice, this list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above copyright
   notice, this list of conditions and the following disclaimer in the
   documentation and/or other materials provided with the distribution.
3. Neither the name of the copyright holders nor the names of its
   contributors may be used to endorse or promote products derived from
   this software without specific prior written permission.

THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
THE POSSIBILITY OF SUCH DAMAGE.
jacoco-0.8.11/org.jacoco.build/licenses/googlecodeprettify-20100721.html000066400000000000000000000242201451257705100254530ustar00rootroot00000000000000

Google Code Prettify

Google Code Prettify 2010/07/21 is subject to the terms and conditions of the following license:

Copyright 2011 Mike Samuel et al

                                 Apache License
                           Version 2.0, January 2004
                        http://www.apache.org/licenses/

   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION

   1. Definitions.

      "License" shall mean the terms and conditions for use, reproduction,
      and distribution as defined by Sections 1 through 9 of this document.

      "Licensor" shall mean the copyright owner or entity authorized by
      the copyright owner that is granting the License.

      "Legal Entity" shall mean the union of the acting entity and all
      other entities that control, are controlled by, or are under common
      control with that entity. For the purposes of this definition,
      "control" means (i) the power, direct or indirect, to cause the
      direction or management of such entity, whether by contract or
      otherwise, or (ii) ownership of fifty percent (50%) or more of the
      outstanding shares, or (iii) beneficial ownership of such entity.

      "You" (or "Your") shall mean an individual or Legal Entity
      exercising permissions granted by this License.

      "Source" form shall mean the preferred form for making modifications,
      including but not limited to software source code, documentation
      source, and configuration files.

      "Object" form shall mean any form resulting from mechanical
      transformation or translation of a Source form, including but
      not limited to compiled object code, generated documentation,
      and conversions to other media types.

      "Work" shall mean the work of authorship, whether in Source or
      Object form, made available under the License, as indicated by a
      copyright notice that is included in or attached to the work
      (an example is provided in the Appendix below).

      "Derivative Works" shall mean any work, whether in Source or Object
      form, that is based on (or derived from) the Work and for which the
      editorial revisions, annotations, elaborations, or other modifications
      represent, as a whole, an original work of authorship. For the purposes
      of this License, Derivative Works shall not include works that remain
      separable from, or merely link (or bind by name) to the interfaces of,
      the Work and Derivative Works thereof.

      "Contribution" shall mean any work of authorship, including
      the original version of the Work and any modifications or additions
      to that Work or Derivative Works thereof, that is intentionally
      submitted to Licensor for inclusion in the Work by the copyright owner
      or by an individual or Legal Entity authorized to submit on behalf of
      the copyright owner. For the purposes of this definition, "submitted"
      means any form of electronic, verbal, or written communication sent
      to the Licensor or its representatives, including but not limited to
      communication on electronic mailing lists, source code control systems,
      and issue tracking systems that are managed by, or on behalf of, the
      Licensor for the purpose of discussing and improving the Work, but
      excluding communication that is conspicuously marked or otherwise
      designated in writing by the copyright owner as "Not a Contribution."

      "Contributor" shall mean Licensor and any individual or Legal Entity
      on behalf of whom a Contribution has been received by Licensor and
      subsequently incorporated within the Work.

   2. Grant of Copyright License. Subject to the terms and conditions of
      this License, each Contributor hereby grants to You a perpetual,
      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
      copyright license to reproduce, prepare Derivative Works of,
      publicly display, publicly perform, sublicense, and distribute the
      Work and such Derivative Works in Source or Object form.

   3. Grant of Patent License. Subject to the terms and conditions of
      this License, each Contributor hereby grants to You a perpetual,
      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
      (except as stated in this section) patent license to make, have made,
      use, offer to sell, sell, import, and otherwise transfer the Work,
      where such license applies only to those patent claims licensable
      by such Contributor that are necessarily infringed by their
      Contribution(s) alone or by combination of their Contribution(s)
      with the Work to which such Contribution(s) was submitted. If You
      institute patent litigation against any entity (including a
      cross-claim or counterclaim in a lawsuit) alleging that the Work
      or a Contribution incorporated within the Work constitutes direct
      or contributory patent infringement, then any patent licenses
      granted to You under this License for that Work shall terminate
      as of the date such litigation is filed.

   4. Redistribution. You may reproduce and distribute copies of the
      Work or Derivative Works thereof in any medium, with or without
      modifications, and in Source or Object form, provided that You
      meet the following conditions:

      (a) You must give any other recipients of the Work or
          Derivative Works a copy of this License; and

      (b) You must cause any modified files to carry prominent notices
          stating that You changed the files; and

      (c) You must retain, in the Source form of any Derivative Works
          that You distribute, all copyright, patent, trademark, and
          attribution notices from the Source form of the Work,
          excluding those notices that do not pertain to any part of
          the Derivative Works; and

      (d) If the Work includes a "NOTICE" text file as part of its
          distribution, then any Derivative Works that You distribute must
          include a readable copy of the attribution notices contained
          within such NOTICE file, excluding those notices that do not
          pertain to any part of the Derivative Works, in at least one
          of the following places: within a NOTICE text file distributed
          as part of the Derivative Works; within the Source form or
          documentation, if provided along with the Derivative Works; or,
          within a display generated by the Derivative Works, if and
          wherever such third-party notices normally appear. The contents
          of the NOTICE file are for informational purposes only and
          do not modify the License. You may add Your own attribution
          notices within Derivative Works that You distribute, alongside
          or as an addendum to the NOTICE text from the Work, provided
          that such additional attribution notices cannot be construed
          as modifying the License.

      You may add Your own copyright statement to Your modifications and
      may provide additional or different license terms and conditions
      for use, reproduction, or distribution of Your modifications, or
      for any such Derivative Works as a whole, provided Your use,
      reproduction, and distribution of the Work otherwise complies with
      the conditions stated in this License.

   5. Submission of Contributions. Unless You explicitly state otherwise,
      any Contribution intentionally submitted for inclusion in the Work
      by You to the Licensor shall be under the terms and conditions of
      this License, without any additional terms or conditions.
      Notwithstanding the above, nothing herein shall supersede or modify
      the terms of any separate license agreement you may have executed
      with Licensor regarding such Contributions.

   6. Trademarks. This License does not grant permission to use the trade
      names, trademarks, service marks, or product names of the Licensor,
      except as required for reasonable and customary use in describing the
      origin of the Work and reproducing the content of the NOTICE file.

   7. Disclaimer of Warranty. Unless required by applicable law or
      agreed to in writing, Licensor provides the Work (and each
      Contributor provides its Contributions) on an "AS IS" BASIS,
      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
      implied, including, without limitation, any warranties or conditions
      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
      PARTICULAR PURPOSE. You are solely responsible for determining the
      appropriateness of using or redistributing the Work and assume any
      risks associated with Your exercise of permissions under this License.

   8. Limitation of Liability. In no event and under no legal theory,
      whether in tort (including negligence), contract, or otherwise,
      unless required by applicable law (such as deliberate and grossly
      negligent acts) or agreed to in writing, shall any Contributor be
      liable to You for damages, including any direct, indirect, special,
      incidental, or consequential damages of any character arising as a
      result of this License or out of the use or inability to use the
      Work (including but not limited to damages for loss of goodwill,
      work stoppage, computer failure or malfunction, or any and all
      other commercial damages or losses), even if such Contributor
      has been advised of the possibility of such damages.

   9. Accepting Warranty or Additional Liability. While redistributing
      the Work or Derivative Works thereof, You may choose to offer,
      and charge a fee for, acceptance of support, warranty, indemnity,
      or other liability obligations and/or rights consistent with this
      License. However, in accepting such obligations, You may act only
      on Your own behalf and on Your sole responsibility, not on behalf
      of any other Contributor, and only if You agree to indemnify,
      defend, and hold each Contributor harmless for any liability
      incurred by, or claims asserted against, such Contributor by reason
      of your accepting any such warranty or additional liability.
jacoco-0.8.11/org.jacoco.build/pom.xml000066400000000000000000001254241451257705100175150ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.build 0.8.11 pom JaCoCo JaCoCo - Java Code Coverage Library http://jacoco.org 2009 Mountainminds GmbH & Co. KG Eclipse Public License 2.0 https://www.eclipse.org/legal/epl-2.0/ repo mtnminds Marc R. Hoffmann hoffmann@mountainminds.com +1 Project Lead brock_j Brock Janiczak brockj@gmail.com +10 Developer mandrikov Evgeny Mandrikov mandrikov@gmail.com http://godin.net.ru SonarSource http://www.sonarsource.com +3 Build and release manager mfriedenhagen Mirko Friedenhagen mfriedenhagen@gmail.com +1 Developer Radek Liba Christoph Beck ../org.jacoco.core ../org.jacoco.report ../org.jacoco.agent.rt ../org.jacoco.agent ../org.jacoco.ant ../org.jacoco.cli ../org.jacoco.examples ../jacoco-maven-plugin ../org.jacoco.tests ../org.jacoco.doc ../jacoco scm:git:git://github.com/jacoco/jacoco.git scm:git:ssh://git@github.com:jacoco/jacoco.git https://github.com/jacoco/jacoco GitHub https://github.com/jacoco/jacoco/issues sonatype-nexus-staging Nexus Release Repository https://oss.sonatype.org/service/local/staging/deploy/maven2/ sonatype-nexus-snapshots Sonatype Nexus Snapshots ${sonatypeOssDistMgmtSnapshotsUrl} UTF-8 https://oss.sonatype.org/content/repositories/snapshots/ yyyyMMddhhmm http://www.jacoco.org/jacoco ${project.inceptionYear}, 2023 1.5 ${bytecode.version} ${bytecode.version} ${jvm.args} 9.6 1.9.16 2.0.28 4.13.1 20100721 ../org.jacoco.doc/target/site/jacoco-aggregate/jacoco.xml ../${project.artifactId}.test/target/surefire-reports/ 1.5 1.5 ${project.groupId} org.jacoco.core ${project.version} ${project.groupId} org.jacoco.report ${project.version} ${project.groupId} org.jacoco.agent ${project.version} ${project.groupId} org.jacoco.agent runtime ${project.version} ${project.groupId} org.jacoco.agent.rt ${project.version} ${project.groupId} org.jacoco.ant ${project.version} ${project.groupId} org.jacoco.ant nodeps ${project.version} ${project.groupId} org.jacoco.cli ${project.version} ${project.groupId} org.jacoco.examples ${project.version} org.ow2.asm asm-bom ${asm.version} pom import org.apache.ant ant ${ant.version} org.apache.ant ant-junit ${ant.version} org.apache.ant ant-junit4 ${ant.version} org.apache.ant ant-launcher ${ant.version} org.apache.ant ant-antunit 1.4 args4j args4j ${args4j.version} junit junit ${junit.version} src false **/*.java **/*.kt **/*.groovy **/*.scala **/*.properties src true **/*.properties **/*-test.properties src false **/*-test.properties . true about.html org.apache.maven.plugins maven-antrun-plugin 3.1.0 org.apache.maven.plugins maven-assembly-plugin 3.6.0 org.apache.maven.plugins maven-clean-plugin 3.2.0 org.apache.maven.plugins maven-compiler-plugin 3.11.0 org.apache.maven.plugins maven-dependency-plugin 3.6.0 org.apache.maven.plugins maven-deploy-plugin 3.1.1 org.apache.maven.plugins maven-enforcer-plugin 3.3.0 org.apache.maven.plugins maven-install-plugin 3.1.1 org.apache.maven.plugins maven-invoker-plugin 2.0.0 org.apache.maven.plugins maven-gpg-plugin 3.1.0 org.apache.maven.plugins maven-jar-plugin 3.3.0 org.apache.maven.plugins maven-javadoc-plugin 3.0.1 true false org.apache.maven.plugins maven-plugin-plugin 3.6.0 org.ow2.asm asm 7.1 org.apache.maven.plugins maven-release-plugin 2.1 true forked-path false -Prelease org.apache.maven.plugins maven-resources-plugin 3.3.1 org.apache.maven.plugins maven-shade-plugin 3.5.0 org.apache.maven.plugins maven-source-plugin 3.3.0 org.apache.maven.plugins maven-surefire-plugin 2.19.1 org.apache.maven.plugins maven-site-plugin 3.3 org.apache.maven.plugins maven-toolchains-plugin 3.1.0 org.codehaus.mojo animal-sniffer-maven-plugin 1.23 org.codehaus.mojo build-helper-maven-plugin 3.4.0 org.codehaus.mojo buildnumber-maven-plugin 3.1.0 org.codehaus.mojo xml-maven-plugin 1.1.0 org.codehaus.mojo exec-maven-plugin 3.1.0 com.github.genthaler beanshell-maven-plugin 1.4 org.apache.felix maven-bundle-plugin 3.5.1 com.diffplug.spotless spotless-maven-plugin 2.37.0 org.apache.maven.plugins maven-surefire-plugin ${project.build.sourceDirectory} ${project.build.outputDirectory} org.apache.maven.plugins maven-shade-plugin false *:* META-INF/*.SF META-INF/*.DSA META-INF/*.RSA org.apache.maven.plugins maven-assembly-plugin 420 493 493 org.apache.maven.plugins maven-enforcer-plugin enforce validate enforce 17 [3.5.4,3.8.2),(3.8.2,) The rules for repo1.maven.org are that pom.xml files should not include repository definitions. true true No SNAPSHOT versions allowed for dependencies true com.diffplug.spotless spotless-maven-plugin UNIX src/**/*.java 4.28 ../org.jacoco.core/.settings/org.eclipse.jdt.core.prefs **/*.properties **/*.html **/*.css **/*.js **/*.xml **/*.xsl **/*.dtd target/** UNIX prepare-package check org.apache.maven.plugins maven-antrun-plugin check-license-header validate run org.codehaus.mojo build-helper-maven-plugin parse-version validate parse-version org.codehaus.mojo buildnumber-maven-plugin validate create false false true 0000000 build.commitId com.github.genthaler beanshell-maven-plugin parse-version validate run true org.apache.felix maven-bundle-plugin ${project.artifactId} ${qualified.bundle.version} ${project.description} !about.html, *.internal*;x-internal:=true;version="${version;===;${Bundle-Version}}", *;version="${version;===;${Bundle-Version}}" org.jacoco.*;version="${range;[===,==+);${Bundle-Version}}", org.objectweb.asm.*;version="${range;[===,=+);${asm.version}}" J2SE-1.5 scm:git:git://github.com/jacoco/jacoco.git;path="${project.artifactId}";commitId=${build.commitId} maven-jdk9 [9,12) 6 maven-jdk12 [12,) 7 integration-tests jdk.version org.apache.maven.plugins maven-toolchains-plugin validate toolchain ${jdk.version} java14-bytecode bytecode.version 14 13 13 java15-bytecode bytecode.version 15 13 13 java16-bytecode bytecode.version 16 13 13 java17-bytecode bytecode.version 17 13 13 java18-bytecode bytecode.version 18 13 13 java19-bytecode bytecode.version 19 13 13 java20-bytecode bytecode.version 20 13 13 java21-bytecode bytecode.version 21 13 13 java22-bytecode bytecode.version 22 13 13 ecj ecj org.apache.maven.plugins maven-compiler-plugin eclipse org.eclipse.jdt ecj 3.34.0 org.codehaus.plexus plexus-compiler-eclipse 2.8.5 jdk6 jdk.version 6 -XX:-FailOverToOldVerifier -Xverify:all jdk7 jdk.version 7 -XX:-FailOverToOldVerifier -Xverify:all jdk8 jdk.version 8 -XX:-FailOverToOldVerifier -Xverify:all jdk9 jdk.version 9 6 jdk10 jdk.version 10 6 jdk11 jdk.version 11 6 jdk12 jdk.version 12 7 sources src/ org.apache.maven.plugins maven-source-plugin attach-sources verify jar-no-fork org.apache.maven.plugins maven-javadoc-plugin attach-javadocs jar release org.apache.maven.plugins maven-enforcer-plugin false enforce-release-rules verify enforce build.commitId [0-9a-f]{40} org.codehaus.mojo animal-sniffer-maven-plugin enforce-java-api-compatibility verify check org.codehaus.mojo.signature java15 1.0 org.apache.maven.plugins maven-gpg-plugin sign-artifacts verify sign m2e m2e.version org.eclipse.m2e lifecycle-mapping 1.0.0 org.apache.maven.plugins maven-antrun-plugin [0,) run org.apache.maven.plugins maven-invoker-plugin [0,) install org.apache.maven.plugins maven-dependency-plugin [0,) unpack copy-dependencies org.codehaus.groovy.maven gmaven-plugin [0,) execute org.codehaus.mojo xml-maven-plugin [0,) transform org.jacoco jacoco-maven-plugin [0,) prepare-agent org.apache.maven.plugins maven-enforcer-plugin [0,) enforce org.codehaus.mojo build-helper-maven-plugin [0,) parse-version jacoco-0.8.11/org.jacoco.cli.test/000077500000000000000000000000001451257705100166165ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli.test/.classpath000066400000000000000000000014151451257705100206020ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.cli.test/.project000066400000000000000000000013341451257705100202660ustar00rootroot00000000000000 org.jacoco.cli.test org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.cli.test/pom.xml000066400000000000000000000024341451257705100201360ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.tests 0.8.11 ../org.jacoco.tests org.jacoco.cli.test JaCoCo :: Test :: Command Line Interface org.jacoco.cli.* ${project.groupId} org.jacoco.cli junit junit jacoco-0.8.11/org.jacoco.cli.test/src/000077500000000000000000000000001451257705100174055ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli.test/src/org/000077500000000000000000000000001451257705100201745ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/000077500000000000000000000000001451257705100214325ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/000077500000000000000000000000001451257705100222015ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/internal/000077500000000000000000000000001451257705100240155ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/internal/CommandTestBase.java000066400000000000000000000042511451257705100276730ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import java.io.PrintWriter; import java.io.StringWriter; import java.io.UnsupportedEncodingException; import java.net.URLDecoder; import org.junit.Before; /** * Base class for command tests. */ public abstract class CommandTestBase { protected StringWriter out; protected StringWriter err; protected int result; @Before public void before() { out = new StringWriter(); err = new StringWriter(); } protected int execute(String... args) throws Exception { result = new Main(args).execute(new PrintWriter(out), new PrintWriter(err)); return result; } protected void assertOk() { assertEquals(err.toString(), 0, result); } protected void assertFailure() { assertEquals(-1, result); } protected void assertNoOutput(StringWriter buffer) { assertEquals("", buffer.toString()); } protected void assertContains(String expected, StringWriter buffer) { final String content = buffer.toString(); assertTrue(content, content.contains(expected)); } protected void assertContainsNot(String expected, StringWriter buffer) { final String content = buffer.toString(); assertFalse(content, content.contains(expected)); } protected String getClassPath() { final String name = getClass().getName(); final String res = "/" + name.replace('.', '/') + ".class"; String loc = getClass().getResource(res).getFile(); try { loc = URLDecoder.decode(loc, "UTF-8"); } catch (UnsupportedEncodingException e) { } return loc.substring(0, loc.length() - res.length()); } } jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/internal/MainTest.java000066400000000000000000000042141451257705100264050ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal; import org.junit.Test; /** * Unit tests for {@link Main}. */ public class MainTest extends CommandTestBase { @Test public void should_print_usage_when_no_arguments_given() throws Exception { execute(); assertFailure(); assertNoOutput(out); assertContains("\"\"", err); assertContains("Usage: java -jar jacococli.jar --help | ", err); assertContains("Command line interface for JaCoCo.", err); } @Test public void should_print_error_message_when_invalid_command_is_given() throws Exception { execute("foo"); assertFailure(); assertNoOutput(out); assertContains("\"foo\" is not a valid value for \"\"", err); assertContains("Usage: java -jar jacococli.jar --help | ", err); } @Test public void should_print_general_usage_when_help_option_is_given() throws Exception { execute("--help"); assertOk(); assertNoOutput(err); assertContains("Usage: java -jar jacococli.jar --help | ", out); assertContains(" : dump|instrument|merge|report", out); } @Test public void should_print_command_usage_when_command_and_help_option_is_given() throws Exception { execute("dump", "--help"); assertOk(); assertNoOutput(err); assertContains("Usage: java -jar jacococli.jar dump", out); assertContains( "Request execution data from a JaCoCo agent running in 'tcpserver' output mode.", out); } @Test public void should_not_print_any_output_when_quiet_option_is_given() throws Exception { execute("version", "--quiet"); assertOk(); assertNoOutput(out); assertNoOutput(err); } } jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/internal/XmlDocumentationTest.java000066400000000000000000000070731451257705100310210ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.io.File; import java.io.FileInputStream; import java.io.InputStream; import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import javax.xml.xpath.XPath; import javax.xml.xpath.XPathConstants; import javax.xml.xpath.XPathExpressionException; import javax.xml.xpath.XPathFactory; import org.junit.Before; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TemporaryFolder; import org.w3c.dom.Document; import org.xml.sax.ErrorHandler; import org.xml.sax.InputSource; import org.xml.sax.SAXException; import org.xml.sax.SAXParseException; /** * Unit tests for {@link XmlDocumentation}. */ public class XmlDocumentationTest { @Rule public TemporaryFolder tmp = new TemporaryFolder(); private DocumentBuilder builder; private XPath xpath; @Before public void before() throws Exception { final DocumentBuilderFactory builderFactory = DocumentBuilderFactory .newInstance(); builder = builderFactory.newDocumentBuilder(); builder.setErrorHandler(new ErrorHandler() { public void error(SAXParseException exception) throws SAXException { fail(exception.getMessage()); } public void fatalError(SAXParseException exception) throws SAXException { fail(exception.getMessage()); } public void warning(SAXParseException exception) throws SAXException { fail(exception.getMessage()); } }); xpath = XPathFactory.newInstance().newXPath(); } @Test public void should_create_documentation() throws Exception { File file = new File(tmp.getRoot(), "doc.xml"); XmlDocumentation.main(file.getAbsolutePath()); Document doc = parse(file); assertContains("java -jar jacococli.jar report", "/documentation/command[@name='report']/usage/text()", doc); assertContains("Generate reports", "/documentation/command[@name='report']/description/text()", doc); assertContains("", "/documentation/command[@name='report']/option[1]/usage/text()", doc); assertContains("false", "/documentation/command[@name='report']/option[1]/@required", doc); assertContains("true", "/documentation/command[@name='report']/option[1]/@multiple", doc); assertContains("-classfiles ", "/documentation/command[@name='report']/option[2]/usage/text()", doc); assertContains("true", "/documentation/command[@name='report']/option[2]/@multiple", doc); } private Document parse(File file) throws Exception { InputStream in = new FileInputStream(file); try { return builder.parse(new InputSource(in)); } finally { in.close(); } } private void assertContains(String expected, String query, Document doc) throws XPathExpressionException { final String actual = eval(query, doc); assertTrue(actual, actual.contains(expected)); } private String eval(String query, Document doc) throws XPathExpressionException { return (String) xpath.evaluate(query, doc, XPathConstants.STRING); } } jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/internal/commands/000077500000000000000000000000001451257705100256165ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/internal/commands/ClassInfoTest.java000066400000000000000000000033241451257705100312040ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal.commands; import org.jacoco.cli.internal.CommandTestBase; import org.junit.Test; /** * Unit tests for {@link ClassInfo}. */ public class ClassInfoTest extends CommandTestBase { @Test public void should_print_usage_when_invalid_option_is_given() throws Exception { execute("classinfo", "--invalid"); assertFailure(); assertContains("\"--invalid\"", err); assertContains( "java -jar jacococli.jar classinfo [ ...]", err); } @Test public void should_print_warning_when_no_class_files_are_provided() throws Exception { execute("classinfo"); assertOk(); assertContains("[WARN] No class files provided.", out); } @Test public void should_print_class_info() throws Exception { execute("classinfo", getClassPath()); assertOk(); assertContains("class", out); assertContains("org/jacoco/cli/internal/commands/ClassInfoTest", out); assertContainsNot("method", out); } @Test public void should_print_class_details_when_verbose() throws Exception { execute("classinfo", "--verbose", getClassPath()); assertOk(); assertContains("line", out); assertContains("method", out); assertContains("line", out); } } jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/internal/commands/DumpTest.java000066400000000000000000000071261451257705100302340ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal.commands; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.io.File; import java.io.IOException; import java.net.InetAddress; import java.net.ServerSocket; import java.net.Socket; import org.jacoco.cli.internal.CommandTestBase; import org.jacoco.core.runtime.IRemoteCommandVisitor; import org.jacoco.core.runtime.RemoteControlReader; import org.jacoco.core.runtime.RemoteControlWriter; import org.junit.After; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TemporaryFolder; /** * Unit tests for {@link Dump}. */ public class DumpTest extends CommandTestBase { @Rule public TemporaryFolder tmp = new TemporaryFolder(); private ServerSocket serverSocket; @After public void after() throws IOException { if (serverSocket != null) { serverSocket.close(); } } @Test public void should_print_usage_when_no_argument_is_given() throws Exception { execute("dump"); assertFailure(); assertContains("\"--destfile\"", err); assertContains("java -jar jacococli.jar dump [--address
]", err); } @Test public void should_write_dump() throws Exception { File execfile = new File(tmp.getRoot(), "jacoco.exec"); int port = startMockServer(); execute("dump", "--destfile", execfile.getAbsolutePath(), "--port", String.valueOf(port)); assertOk(); assertContains("[INFO] Connecting to ", out); assertContains("[INFO] Writing execution data to " + execfile.getAbsolutePath(), out); assertTrue(execfile.exists()); } @Test public void should_log_connection_error_when_retry_is_specified() throws Exception { File execfile = new File(tmp.getRoot(), "jacoco.exec"); int port = unusedPort(); try { execute("dump", "--destfile", execfile.getAbsolutePath(), "--port", String.valueOf(port), "--retry", "1"); fail("IOException expected"); } catch (IOException ignore) { } // Locale independent parts of error message: assertContains("[WARN]", err); assertContains("Connection refused", err); } private int startMockServer() throws IOException { serverSocket = new ServerSocket(0, 0, InetAddress.getByName(null)); new Thread() { @Override public void run() { try { serveRequest(serverSocket.accept()); } catch (IOException e) { throw new RuntimeException(e); } } }.start(); return serverSocket.getLocalPort(); } private void serveRequest(Socket socket) throws IOException { final RemoteControlWriter writer = new RemoteControlWriter( socket.getOutputStream()); final RemoteControlReader reader = new RemoteControlReader( socket.getInputStream()); reader.setRemoteCommandVisitor(new IRemoteCommandVisitor() { public void visitDumpCommand(boolean dump, boolean reset) throws IOException { writer.sendCmdOk(); } }); while (reader.read()) { } } private int unusedPort() throws IOException { final ServerSocket serverSocket = new ServerSocket(0, 0, InetAddress.getByName(null)); final int port = serverSocket.getLocalPort(); serverSocket.close(); return port; } } jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/internal/commands/ExecInfoTest.java000066400000000000000000000046171451257705100310310ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal.commands; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import org.jacoco.cli.internal.CommandTestBase; import org.jacoco.core.data.ExecutionData; import org.jacoco.core.data.ExecutionDataWriter; import org.jacoco.core.data.SessionInfo; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TemporaryFolder; /** * Unit tests for {@link ExecInfo}. */ public class ExecInfoTest extends CommandTestBase { @Rule public TemporaryFolder tmp = new TemporaryFolder(); @Test public void should_print_usage_when_invalid_argument_is_given() throws Exception { execute("execinfo", "--invalid"); assertFailure(); assertContains("\"--invalid\"", err); assertContains("java -jar jacococli.jar execinfo [ ...]", err); } @Test public void should_print_warning_when_no_exec_files_are_provided() throws Exception { execute("execinfo"); assertOk(); assertContains("[WARN] No execution data files provided.", out); } @Test public void should_print_execution_data_info() throws Exception { File execfile = createExecFile(); execute("execinfo", execfile.getAbsolutePath()); assertOk(); assertContains("[INFO] Loading exec file " + execfile.getAbsolutePath(), out); assertContains("CLASS ID HITS/PROBES CLASS NAME", out); assertContains("Session \"testid\":", out); assertContains("0000000000001234 2 of 3 foo/MyClass", out); } private File createExecFile() throws IOException { File f = new File(tmp.getRoot(), "test.exec"); final FileOutputStream out = new FileOutputStream(f); final ExecutionDataWriter writer = new ExecutionDataWriter(out); writer.visitSessionInfo(new SessionInfo("testid", 1, 2)); writer.visitClassExecution(new ExecutionData(0x1234, "foo/MyClass", new boolean[] { false, true, true })); out.close(); return f; } } jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/internal/commands/InstrumentTest.java000066400000000000000000000106331451257705100314740ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal.commands; import static org.junit.Assert.assertArrayEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.util.HashSet; import java.util.Set; import org.jacoco.cli.internal.CommandTestBase; import org.jacoco.core.internal.InputStreams; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TemporaryFolder; import org.objectweb.asm.ClassReader; import org.objectweb.asm.ClassVisitor; import org.objectweb.asm.MethodVisitor; /** * Unit tests for {@link Instrument}. */ public class InstrumentTest extends CommandTestBase { @Rule public TemporaryFolder tmp = new TemporaryFolder(); @Test public void should_print_usage_when_no_options_are_given() throws Exception { execute("instrument"); assertFailure(); assertContains("\"--dest\"", err); assertContains( "Usage: java -jar jacococli.jar instrument [ ...]", err); } @Test public void should_instrument_class_files_and_copy_resources_when_folder_is_given() throws Exception { File destdir = tmp.getRoot(); execute("instrument", "--dest", destdir.getAbsolutePath(), getClassPath()); assertOk(); assertContains("[INFO] 14 classes instrumented to " + destdir.getAbsolutePath(), out); // non class-file resources are copied: assertTrue(new File(destdir, "org/jacoco/cli/internal/commands/test-resource.properties") .isFile()); assertInstrumented(new File(destdir, "org/jacoco/cli/internal/commands/InstrumentTest.class")); } @Test public void should_instrument_class_files_to_dest_folder_when_class_files_are_given() throws Exception { File destdir = tmp.getRoot(); File src = new File(getClassPath(), "org/jacoco/cli/internal/commands/InstrumentTest.class"); execute("instrument", "--dest", destdir.getAbsolutePath(), src.getAbsolutePath()); assertOk(); assertContains( "[INFO] 1 classes instrumented to " + destdir.getAbsolutePath(), out); assertInstrumented(new File(destdir, "InstrumentTest.class")); } @Test public void should_not_instrument_anything_when_no_source_is_given() throws Exception { File destdir = tmp.getRoot(); execute("instrument", "--dest", destdir.getAbsolutePath()); assertOk(); assertArrayEquals(new String[0], destdir.list()); } @Test public void should_not_create_dest_file_when_source_class_is_broken() throws Exception { File srcdir = new File(tmp.getRoot(), "src"); srcdir.mkdir(); File destdir = new File(tmp.getRoot(), "dest"); destdir.mkdir(); OutputStream out = new FileOutputStream( new File(srcdir, "Broken.class")); out.write((byte) 0xca); out.write((byte) 0xfe); out.write((byte) 0xba); out.write((byte) 0xbe); out.write((byte) 0x00); out.write((byte) 0x00); out.write((byte) 0x00); out.write((byte) 50); out.close(); try { execute("instrument", "--dest", destdir.getAbsolutePath(), srcdir.getAbsolutePath()); fail("exception expected"); } catch (IOException expected) { } assertFalse(new File(destdir, "Broken.class").exists()); } private void assertInstrumented(File classfile) throws IOException { InputStream in = new FileInputStream(classfile); final ClassReader reader = InstrSupport .classReaderFor(InputStreams.readFully(in)); in.close(); final Set methods = new HashSet(); reader.accept(new ClassVisitor(InstrSupport.ASM_API_VERSION) { @Override public MethodVisitor visitMethod(int access, String name, String descriptor, String signature, String[] exceptions) { methods.add(name); return null; } }, 0); assertTrue(methods.contains("$jacocoInit")); } } jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/internal/commands/MergeTest.java000066400000000000000000000057301451257705100303650ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal.commands; import static org.junit.Assert.assertEquals; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.util.Arrays; import java.util.Collections; import java.util.HashSet; import java.util.Set; import org.jacoco.cli.internal.CommandTestBase; import org.jacoco.core.data.ExecutionData; import org.jacoco.core.data.ExecutionDataWriter; import org.jacoco.core.tools.ExecFileLoader; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TemporaryFolder; /** * Unit tests for {@link Merge}. */ public class MergeTest extends CommandTestBase { @Rule public TemporaryFolder tmp = new TemporaryFolder(); @Test public void should_print_usage_when_no_options_are_given() throws Exception { execute("merge"); assertFailure(); assertContains("\"--destfile\"", err); assertContains("java -jar jacococli.jar merge [ ...]", err); } @Test public void should_print_warning_when_no_exec_files_are_provided() throws Exception { File dest = new File(tmp.getRoot(), "merged.exec"); execute("merge", "--destfile", dest.getAbsolutePath()); assertOk(); assertContains("[WARN] No execution data files provided.", out); Set names = loadExecFile(dest); assertEquals(Collections.emptySet(), names); } @Test public void should_merge_exec_files() throws Exception { File a = createExecFile("a"); File b = createExecFile("b"); File c = createExecFile("c"); File dest = new File(tmp.getRoot(), "merged.exec"); execute("merge", "--destfile", dest.getAbsolutePath(), a.getAbsolutePath(), b.getAbsolutePath(), c.getAbsolutePath()); assertOk(); Set names = loadExecFile(dest); assertEquals(new HashSet(Arrays.asList("a", "b", "c")), names); } private File createExecFile(String name) throws IOException { File file = new File(tmp.getRoot(), name + ".exec"); final FileOutputStream execout = new FileOutputStream(file); ExecutionDataWriter writer = new ExecutionDataWriter(execout); writer.visitClassExecution(new ExecutionData(name.hashCode(), name, new boolean[] { true })); execout.close(); return file; } private Set loadExecFile(File file) throws IOException { ExecFileLoader loader = new ExecFileLoader(); loader.load(file); Set names = new HashSet(); for (ExecutionData d : loader.getExecutionDataStore().getContents()) { names.add(d.getName()); } return names; } } jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/internal/commands/ReportTest.java000066400000000000000000000105641451257705100306020ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal.commands; import static org.junit.Assert.assertTrue; import java.io.File; import java.io.FileOutputStream; import org.jacoco.cli.internal.CommandTestBase; import org.jacoco.core.data.ExecutionData; import org.jacoco.core.data.ExecutionDataWriter; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TemporaryFolder; /** * Unit tests for {@link Report}. */ public class ReportTest extends CommandTestBase { @Rule public TemporaryFolder tmp = new TemporaryFolder(); @Test public void should_print_usage_when_no_options_are_given() throws Exception { execute("report"); assertFailure(); assertContains("\"--classfiles\"", err); assertContains( "Usage: java -jar jacococli.jar report [ ...]", err); } @Test public void should_print_warning_when_no_exec_files_are_provided() throws Exception { execute("report", "--classfiles", getClassPath()); assertOk(); assertContains("[WARN] No execution data files provided.", out); } @Test public void should_print_number_of_analyzed_classes() throws Exception { execute("report", "--classfiles", getClassPath()); assertOk(); assertContains("[INFO] Analyzing 14 classes.", out); } @Test public void should_print_warning_when_exec_data_does_not_match() throws Exception { File exec = new File(tmp.getRoot(), "jacoco.exec"); final FileOutputStream execout = new FileOutputStream(exec); ExecutionDataWriter writer = new ExecutionDataWriter(execout); // Add probably invalid id for this test class: writer.visitClassExecution( new ExecutionData(0x123, getClass().getName().replace('.', '/'), new boolean[] { true })); execout.close(); execute("report", exec.getAbsolutePath(), "--classfiles", getClassPath()); assertOk(); assertContains("[WARN] Some classes do not match with execution data.", out); assertContains( "[WARN] For report generation the same class files must be used as at runtime.", out); assertContains( "[WARN] Execution data for class org/jacoco/cli/internal/commands/ReportTest does not match.", out); } @Test public void should_create_xml_report_when_xml_option_is_provided() throws Exception { File xml = new File(tmp.getRoot(), "coverage.xml"); execute("report", "--classfiles", getClassPath(), "--xml", xml.getAbsolutePath()); assertOk(); assertTrue(xml.isFile()); } @Test public void should_create_csv_report_when_csv_option_is_provided() throws Exception { File csv = new File(tmp.getRoot(), "coverage.csv"); execute("report", "--classfiles", getClassPath(), "--csv", csv.getAbsolutePath()); assertOk(); assertTrue(csv.isFile()); } @Test public void should_create_html_report_when_html_option_is_provided() throws Exception { File html = new File(tmp.getRoot(), "coverage"); execute("report", "--classfiles", getClassPath(), "--sourcefiles", "./src", "--html", html.getAbsolutePath()); assertOk(); assertTrue(html.isDirectory()); assertTrue(new File(html, "org.jacoco.cli.internal.commands/ReportTest.html").isFile()); assertTrue(new File(html, "org.jacoco.cli.internal.commands/ReportTest.java.html") .isFile()); } @Test public void should_use_all_values_when_multiple_classfiles_options_are_provided() throws Exception { File html = new File(tmp.getRoot(), "coverage"); final String c1 = getClassPath() + "/org/jacoco/cli/internal/commands/ReportTest.class"; final String c2 = getClassPath() + "/org/jacoco/cli/internal/commands/DumpTest.class"; execute("report", "--classfiles", c1, "--classfiles", c2, "--html", html.getAbsolutePath()); assertOk(); assertTrue(html.isDirectory()); assertTrue(new File(html, "org.jacoco.cli.internal.commands/ReportTest.html").isFile()); assertTrue( new File(html, "org.jacoco.cli.internal.commands/DumpTest.html") .isFile()); } } jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/internal/commands/VersionTest.java000066400000000000000000000016301451257705100307460ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal.commands; import org.jacoco.cli.internal.CommandTestBase; import org.jacoco.core.JaCoCo; import org.junit.Test; /** * Unit tests for {@link Version}. */ public class VersionTest extends CommandTestBase { @Test public void should_print_version() throws Exception { execute("version"); assertOk(); assertContains(JaCoCo.VERSION, out); } } jacoco-0.8.11/org.jacoco.cli.test/src/org/jacoco/cli/internal/commands/test-resource.properties000066400000000000000000000000051451257705100325330ustar00rootroot00000000000000x=42 jacoco-0.8.11/org.jacoco.cli/000077500000000000000000000000001451257705100156405ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli/.classpath000066400000000000000000000014151451257705100176240ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.cli/.project000066400000000000000000000013601451257705100173070ustar00rootroot00000000000000 org.jacoco.cli org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core/.settings jacoco-0.8.11/org.jacoco.cli/about.html000066400000000000000000000017441451257705100176460ustar00rootroot00000000000000 About

About This Content

${build.date}

License

All Content in this distribution is made available by Mountainminds GmbH & Co. KG, Munich. Unless otherwise indicated below, the Content is provided to you under the terms and conditions of the Eclipse Public License Version 2.0 ("EPL"). A copy of the EPL is available at https://www.eclipse.org/legal/epl-2.0/. For purposes of the EPL, "Program" will mean the Content.

The Content includes items that have been sourced from third parties as set out below.

${args4j.license} ${asm.license} ${googlecodeprettify.license} jacoco-0.8.11/org.jacoco.cli/pom.xml000066400000000000000000000112401451257705100171530ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.build 0.8.11 ../org.jacoco.build org.jacoco.cli JaCoCo :: Command Line Interface JaCoCo Command Line Interface ${project.groupId} org.jacoco.core ${project.groupId} org.jacoco.report args4j args4j src org.codehaus.mojo exec-maven-plugin package exec jdk java -cp org.jacoco.cli.internal.XmlDocumentation ${project.build.directory}/generated-documentation/cli.xml org.apache.maven.plugins maven-shade-plugin package shade true nodeps true org.objectweb.asm org.jacoco.cli.internal.asm org.kohsuke.args4j org.jacoco.cli.internal.args4j org.jacoco.core org.jacoco.cli.internal.core org.jacoco.report org.jacoco.cli.internal.report ${project.description} ${project.organization.name} ${project.version} org.jacoco.cli.internal.Main args4j:args4j **/Messages_*.properties org.ow2.asm:* module-info.class jacoco-0.8.11/org.jacoco.cli/src/000077500000000000000000000000001451257705100164275ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli/src/org/000077500000000000000000000000001451257705100172165ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/000077500000000000000000000000001451257705100204545ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/000077500000000000000000000000001451257705100212235ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/000077500000000000000000000000001451257705100230375ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/Command.java000066400000000000000000000045541451257705100252700ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal; import java.io.PrintWriter; import java.io.StringWriter; import org.kohsuke.args4j.Option; /** * Common interface for all commands. */ public abstract class Command { /** * Common command line prefix. */ public static final String JAVACMD = "java -jar jacococli.jar "; /** * Flag whether help should be printed for this command. */ @Option(name = "--help", usage = "show help", help = true) public boolean help = false; /** * Flag whether output to stdout should be suppressed. */ @Option(name = "--quiet", usage = "suppress all output on stdout") public boolean quiet = false; /** * @return Short description of the command. */ public abstract String description(); /** * @return name of the command */ public String name() { return getClass().getSimpleName().toLowerCase(); } /** * @param parser * parser for this command * @return usage string displayed for help */ public String usage(final CommandParser parser) { final StringWriter writer = new StringWriter(); parser.printSingleLineUsage(writer, null); return JAVACMD + name() + writer; } /** * Executes the given command. * * @param out * std out * @param err * std err * @return exit code, should be 0 for normal operation * @throws Exception * any exception that my occur during execution */ public abstract int execute(PrintWriter out, PrintWriter err) throws Exception; /** * Prints textual help for this command. * * @param writer * output destination */ protected void printHelp(final PrintWriter writer) { final CommandParser parser = new CommandParser(this); writer.println(description()); writer.println(); writer.println("Usage: " + parser.getCommand().usage(parser)); parser.printUsage(writer, null); } } jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/CommandHandler.java000066400000000000000000000050721451257705100265620ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal; import java.util.AbstractList; import org.jacoco.cli.internal.commands.AllCommands; import org.kohsuke.args4j.CmdLineException; import org.kohsuke.args4j.CmdLineParser; import org.kohsuke.args4j.OptionDef; import org.kohsuke.args4j.spi.Messages; import org.kohsuke.args4j.spi.OptionHandler; import org.kohsuke.args4j.spi.Parameters; import org.kohsuke.args4j.spi.Setter; /** * {@link OptionHandler} which uses {@link CommandParser} internally to provide * help context also for sub-commands. */ public class CommandHandler extends OptionHandler { /** * This constructor is required by the args4j framework. * * @param parser * @param option * @param setter */ public CommandHandler(final CmdLineParser parser, final OptionDef option, final Setter setter) { super(parser, new OptionDef(AllCommands.names(), "", option.required(), option.help(), option.hidden(), CommandHandler.class, option.isMultiValued()) { }, setter); } @Override public int parseArguments(final Parameters params) throws CmdLineException { final String subCmd = params.getParameter(0); for (final Command c : AllCommands.get()) { if (c.name().equals(subCmd)) { parseSubArguments(c, params); setter.addValue(c); return params.size(); // consume all the remaining tokens } } throw new CmdLineException(owner, Messages.ILLEGAL_OPERAND.format(option.toString(), subCmd)); } private void parseSubArguments(final Command c, final Parameters params) throws CmdLineException { final CmdLineParser p = new CommandParser(c); p.parseArgument(new AbstractList() { @Override public String get(final int index) { try { return params.getParameter(index + 1); } catch (final CmdLineException e) { // invalid index was accessed. throw new IndexOutOfBoundsException(); } } @Override public int size() { return params.size() - 1; } }); } @Override public String getDefaultMetaVariable() { return ""; } } jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/CommandParser.java000066400000000000000000000016671451257705100264470ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal; import org.kohsuke.args4j.CmdLineParser; /** * Parser which remembers the parsed command to have additional context * information to produce help output. */ public class CommandParser extends CmdLineParser { private final Command command; CommandParser(final Command command) { super(command); this.command = command; } Command getCommand() { return command; } } jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/Main.java000066400000000000000000000050321451257705100245660ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal; import java.io.IOException; import java.io.PrintWriter; import java.io.Writer; import org.kohsuke.args4j.Argument; import org.kohsuke.args4j.CmdLineException; /** * Entry point for all command line operations. */ public class Main extends Command { private static final PrintWriter NUL = new PrintWriter(new Writer() { @Override public void write(final char[] arg0, final int arg1, final int arg2) throws IOException { } @Override public void flush() throws IOException { } @Override public void close() throws IOException { } }); private final String[] args; Main(final String... args) { this.args = args; } @Argument(handler = CommandHandler.class, required = true) Command command; @Override public String description() { return "Command line interface for JaCoCo."; } @Override public String usage(final CommandParser parser) { return JAVACMD + "--help | "; } @Override public int execute(PrintWriter out, final PrintWriter err) throws Exception { final CommandParser mainParser = new CommandParser(this); try { mainParser.parseArgument(args); } catch (final CmdLineException e) { ((CommandParser) e.getParser()).getCommand().printHelp(err); err.println(); err.println(e.getMessage()); return -1; } if (help) { printHelp(out); return 0; } if (command.help) { command.printHelp(out); return 0; } if (command.quiet) { out = NUL; } return command.execute(out, err); } /** * Main entry point for program invocations. * * @param args * program arguments * @throws Exception * All internal exceptions are directly passed on to get printed * on the console */ public static void main(final String... args) throws Exception { final PrintWriter out = new PrintWriter(System.out, true); final PrintWriter err = new PrintWriter(System.err, true); final int returncode = new Main(args).execute(out, err); System.exit(returncode); } } jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/XmlDocumentation.java000066400000000000000000000047541451257705100272060ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.util.List; import org.jacoco.cli.internal.commands.AllCommands; import org.jacoco.report.internal.xml.XMLElement; import org.kohsuke.args4j.spi.OptionHandler; /** * Internal utility to dump all command descriptions as XML. */ public final class XmlDocumentation { private XmlDocumentation() { } private static void writeCommand(final Command command, final XMLElement parent) throws IOException { final CommandParser parser = new CommandParser(command); final XMLElement element = parent.element("command"); element.attr("name", command.name()); element.element("usage").text(command.usage(parser)); element.element("description").text(command.description()); writeOptions(element, parser.getArguments()); writeOptions(element, parser.getOptions()); } private static void writeOptions(final XMLElement parent, @SuppressWarnings("rawtypes") final List list) throws IOException { for (final OptionHandler o : list) { final XMLElement optionNode = parent.element("option"); optionNode.attr("required", String.valueOf(o.option.required())); optionNode.attr("multiple", String.valueOf(o.setter.isMultiValued())); optionNode.element("usage").text(o.getNameAndMeta(null)); optionNode.element("description").text(o.option.usage()); } } /** * Called during the build process. * * @param args * exactly one argument expected with the target location * @throws IOException * if XML document cannot be written */ public static void main(final String... args) throws IOException { final File file = new File(args[0]); file.getParentFile().mkdirs(); final XMLElement root = new XMLElement("documentation", null, null, true, "UTF-8", new FileOutputStream(file)); for (final Command c : AllCommands.get()) { writeCommand(c, root); } root.close(); } } jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/commands/000077500000000000000000000000001451257705100246405ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/commands/AllCommands.java000066400000000000000000000024351451257705100277010ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal.commands; import java.util.Arrays; import java.util.List; import org.jacoco.cli.internal.Command; /** * List of all available commands. */ public final class AllCommands { private AllCommands() { } /** * @return list of new instances of all available commands */ public static List get() { return Arrays.asList(new Dump(), new Instrument(), new Merge(), new Report(), new ClassInfo(), new ExecInfo(), new Version()); } /** * @return String containing all available command names */ public static String names() { final StringBuilder sb = new StringBuilder(); for (final Command c : get()) { if (sb.length() > 0) { sb.append('|'); } sb.append(c.name()); } return sb.toString(); } } jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/commands/ClassInfo.java000066400000000000000000000073221451257705100273700ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal.commands; import java.io.File; import java.io.IOException; import java.io.PrintWriter; import java.util.ArrayList; import java.util.Iterator; import java.util.List; import org.jacoco.cli.internal.Command; import org.jacoco.core.analysis.Analyzer; import org.jacoco.core.analysis.IClassCoverage; import org.jacoco.core.analysis.ICounter; import org.jacoco.core.analysis.ICoverageNode; import org.jacoco.core.analysis.ICoverageVisitor; import org.jacoco.core.analysis.ILine; import org.jacoco.core.analysis.IMethodCoverage; import org.jacoco.core.data.ExecutionDataStore; import org.kohsuke.args4j.Argument; import org.kohsuke.args4j.Option; /** * The classinfo command. */ public class ClassInfo extends Command { @Argument(usage = "location of Java class files", metaVar = "") List classfiles = new ArrayList(); @Option(name = "--verbose", usage = "show method and line number details") boolean verbose = false; @Override public String description() { return "Print information about Java class files at the provided location."; } @Override public int execute(final PrintWriter out, final PrintWriter err) throws IOException { if (classfiles.isEmpty()) { out.println("[WARN] No class files provided."); } else { final Analyzer analyzer = new Analyzer(new ExecutionDataStore(), new Printer(out)); for (final File file : classfiles) { analyzer.analyzeAll(file); } } return 0; } private class Printer implements ICoverageVisitor { private final PrintWriter out; Printer(final PrintWriter out) { this.out = out; out.println(" INST BRAN LINE METH CXTY ELEMENT"); } public void visitCoverage(final IClassCoverage coverage) { final String desc = String.format("class 0x%016x %s", Long.valueOf(coverage.getId()), coverage.getName()); printDetails(desc, coverage); if (verbose) { for (final Iterator i = coverage.getMethods() .iterator(); i.hasNext();) { printMethod(i.next(), i.hasNext()); } } } private void printMethod(final IMethodCoverage method, final boolean more) { final String desc = String.format("+- method %s%s", method.getName(), method.getDesc()); printDetails(desc, method); for (int nr = method.getFirstLine(); nr <= method .getLastLine(); nr++) { printLine(method.getLine(nr), nr, more ? "| " : " "); } } private void printLine(final ILine line, final int nr, final String indent) { if (line.getStatus() != ICounter.EMPTY) { out.printf("%6s %6s %s +- line %s%n", total(line.getInstructionCounter()), total(line.getBranchCounter()), indent, Integer.valueOf(nr)); } } private void printDetails(final String description, final ICoverageNode coverage) { out.printf("%6s %6s %6s %6s %6s %s%n", total(coverage.getInstructionCounter()), total(coverage.getBranchCounter()), total(coverage.getLineCounter()), total(coverage.getMethodCounter()), total(coverage.getComplexityCounter()), description); } private String total(final ICounter counter) { return String.valueOf(counter.getTotalCount()); } } } jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/commands/Dump.java000066400000000000000000000047241451257705100264170ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal.commands; import java.io.File; import java.io.IOException; import java.io.PrintWriter; import java.net.InetAddress; import org.jacoco.cli.internal.Command; import org.jacoco.core.runtime.AgentOptions; import org.jacoco.core.tools.ExecDumpClient; import org.jacoco.core.tools.ExecFileLoader; import org.kohsuke.args4j.Option; /** * The dump command. */ public class Dump extends Command { @Option(name = "--address", usage = "host name or ip address to connect to (default localhost)", metaVar = "
") String address = AgentOptions.DEFAULT_ADDRESS; @Option(name = "--port", usage = "the port to connect to (default 6300)", metaVar = "") int port = AgentOptions.DEFAULT_PORT; @Option(name = "--destfile", usage = "file to write execution data to", metaVar = "", required = true) File destfile; @Option(name = "--reset", usage = "reset execution data on test target after dump") boolean reset = false; @Option(name = "--retry", usage = "number of retries (default 10)", metaVar = "") int retrycount = 10; @Override public String description() { return "Request execution data from a JaCoCo agent running in 'tcpserver' output mode."; } @Override public int execute(final PrintWriter out, final PrintWriter err) throws Exception { final ExecDumpClient client = new ExecDumpClient() { @Override protected void onConnecting(final InetAddress address, final int port) { out.printf("[INFO] Connecting to %s:%s.%n", address, Integer.valueOf(port)); } @Override protected void onConnectionFailure(final IOException exception) { err.printf("[WARN] %s.%n", exception.getMessage()); } }; client.setReset(reset); client.setRetryCount(retrycount); final ExecFileLoader loader = client.dump(address, port); out.printf("[INFO] Writing execution data to %s.%n", destfile.getAbsolutePath()); loader.save(destfile, true); return 0; } } jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/commands/ExecInfo.java000066400000000000000000000054101451257705100272030ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal.commands; import java.io.File; import java.io.FileInputStream; import java.io.IOException; import java.io.PrintWriter; import java.util.ArrayList; import java.util.Date; import java.util.List; import org.jacoco.cli.internal.Command; import org.jacoco.core.data.ExecutionData; import org.jacoco.core.data.ExecutionDataReader; import org.jacoco.core.data.IExecutionDataVisitor; import org.jacoco.core.data.ISessionInfoVisitor; import org.jacoco.core.data.SessionInfo; import org.kohsuke.args4j.Argument; /** * The execinfo command. */ public class ExecInfo extends Command { @Argument(usage = "list of JaCoCo *.exec files to read", metaVar = "") List execfiles = new ArrayList(); @Override public String description() { return "Print exec file content in human readable format."; } @Override public int execute(final PrintWriter out, final PrintWriter err) throws IOException { if (execfiles.isEmpty()) { out.println("[WARN] No execution data files provided."); } else { for (final File file : execfiles) { dump(file, out); } } return 0; } private void dump(final File file, final PrintWriter out) throws IOException { out.printf("[INFO] Loading exec file %s.%n", file); out.println("CLASS ID HITS/PROBES CLASS NAME"); final FileInputStream in = new FileInputStream(file); final ExecutionDataReader reader = new ExecutionDataReader(in); reader.setSessionInfoVisitor(new ISessionInfoVisitor() { public void visitSessionInfo(final SessionInfo info) { out.printf("Session \"%s\": %s - %s%n", info.getId(), new Date(info.getStartTimeStamp()), new Date(info.getDumpTimeStamp())); } }); reader.setExecutionDataVisitor(new IExecutionDataVisitor() { public void visitClassExecution(final ExecutionData data) { out.printf("%016x %3d of %3d %s%n", Long.valueOf(data.getId()), Integer.valueOf(getHitCount(data.getProbes())), Integer.valueOf(data.getProbes().length), data.getName()); } }); reader.read(); in.close(); out.println(); } private int getHitCount(final boolean[] data) { int count = 0; for (final boolean hit : data) { if (hit) { count++; } } return count; } } jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/commands/Instrument.java000066400000000000000000000056141451257705100276610ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * John Keeping - initial implementation * Marc R. Hoffmann - rework * *******************************************************************************/ package org.jacoco.cli.internal.commands; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.io.PrintWriter; import java.util.ArrayList; import java.util.List; import org.jacoco.cli.internal.Command; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.runtime.OfflineInstrumentationAccessGenerator; import org.kohsuke.args4j.Argument; import org.kohsuke.args4j.Option; /** * The instrument command. */ public class Instrument extends Command { @Option(name = "--dest", usage = "path to write instrumented Java classes to", metaVar = "", required = true) File dest; @Argument(usage = "list of folder or files to instrument recusively", metaVar = "") List source = new ArrayList(); private Instrumenter instrumenter; @Override public String description() { return "Off-line instrumentation of Java class files and JAR files."; } @Override public int execute(final PrintWriter out, final PrintWriter err) throws IOException { final File absoluteDest = dest.getAbsoluteFile(); instrumenter = new Instrumenter( new OfflineInstrumentationAccessGenerator()); int total = 0; for (final File s : source) { if (s.isFile()) { total += instrument(s, new File(absoluteDest, s.getName())); } else { total += instrumentRecursive(s, absoluteDest); } } out.printf("[INFO] %s classes instrumented to %s.%n", Integer.valueOf(total), absoluteDest); return 0; } private int instrumentRecursive(final File src, final File dest) throws IOException { int total = 0; if (src.isDirectory()) { for (final File child : src.listFiles()) { total += instrumentRecursive(child, new File(dest, child.getName())); } } else { total += instrument(src, dest); } return total; } private int instrument(final File src, final File dest) throws IOException { dest.getParentFile().mkdirs(); final InputStream input = new FileInputStream(src); try { final OutputStream output = new FileOutputStream(dest); try { return instrumenter.instrumentAll(input, output, src.getAbsolutePath()); } finally { output.close(); } } catch (final IOException e) { dest.delete(); throw e; } finally { input.close(); } } } jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/commands/Merge.java000066400000000000000000000037551451257705100265540ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal.commands; import java.io.File; import java.io.IOException; import java.io.PrintWriter; import java.util.ArrayList; import java.util.List; import org.jacoco.cli.internal.Command; import org.jacoco.core.tools.ExecFileLoader; import org.kohsuke.args4j.Argument; import org.kohsuke.args4j.Option; /** * The merge command. */ public class Merge extends Command { @Argument(usage = "list of JaCoCo *.exec files to read", metaVar = "") List execfiles = new ArrayList(); @Option(name = "--destfile", usage = "file to write merged execution data to", metaVar = "", required = true) File destfile; @Override public String description() { return "Merges multiple exec files into a new one."; } @Override public int execute(final PrintWriter out, final PrintWriter err) throws IOException { final ExecFileLoader loader = loadExecutionData(out); out.printf("[INFO] Writing execution data to %s.%n", destfile.getAbsolutePath()); loader.save(destfile, true); return 0; } private ExecFileLoader loadExecutionData(final PrintWriter out) throws IOException { final ExecFileLoader loader = new ExecFileLoader(); if (execfiles.isEmpty()) { out.println("[WARN] No execution data files provided."); } else { for (final File file : execfiles) { out.printf("[INFO] Loading execution data file %s.%n", file.getAbsolutePath()); loader.load(file); } } return loader; } } jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/commands/Report.java000066400000000000000000000134361451257705100267650ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * John Keeping - initial implementation * Marc R. Hoffmann - rework * *******************************************************************************/ package org.jacoco.cli.internal.commands; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.PrintWriter; import java.util.ArrayList; import java.util.Collection; import java.util.List; import org.jacoco.cli.internal.Command; import org.jacoco.core.analysis.Analyzer; import org.jacoco.core.analysis.CoverageBuilder; import org.jacoco.core.analysis.IBundleCoverage; import org.jacoco.core.analysis.IClassCoverage; import org.jacoco.core.data.ExecutionDataStore; import org.jacoco.core.tools.ExecFileLoader; import org.jacoco.report.DirectorySourceFileLocator; import org.jacoco.report.FileMultiReportOutput; import org.jacoco.report.IReportVisitor; import org.jacoco.report.ISourceFileLocator; import org.jacoco.report.MultiReportVisitor; import org.jacoco.report.MultiSourceFileLocator; import org.jacoco.report.csv.CSVFormatter; import org.jacoco.report.html.HTMLFormatter; import org.jacoco.report.xml.XMLFormatter; import org.kohsuke.args4j.Argument; import org.kohsuke.args4j.Option; /** * The report command. */ public class Report extends Command { @Argument(usage = "list of JaCoCo *.exec files to read", metaVar = "") List execfiles = new ArrayList(); @Option(name = "--classfiles", usage = "location of Java class files", metaVar = "", required = true) List classfiles = new ArrayList(); @Option(name = "--sourcefiles", usage = "location of the source files", metaVar = "") List sourcefiles = new ArrayList(); @Option(name = "--tabwith", usage = "tab stop width for the source pages (default 4)", metaVar = "") int tabwidth = 4; @Option(name = "--name", usage = "name used for this report", metaVar = "") String name = "JaCoCo Coverage Report"; @Option(name = "--encoding", usage = "source file encoding (by default platform encoding is used)", metaVar = "") String encoding; @Option(name = "--xml", usage = "output file for the XML report", metaVar = "") File xml; @Option(name = "--csv", usage = "output file for the CSV report", metaVar = "") File csv; @Option(name = "--html", usage = "output directory for the HTML report", metaVar = "") File html; @Override public String description() { return "Generate reports in different formats by reading exec and Java class files."; } @Override public int execute(final PrintWriter out, final PrintWriter err) throws IOException { final ExecFileLoader loader = loadExecutionData(out); final IBundleCoverage bundle = analyze(loader.getExecutionDataStore(), out); writeReports(bundle, loader, out); return 0; } private ExecFileLoader loadExecutionData(final PrintWriter out) throws IOException { final ExecFileLoader loader = new ExecFileLoader(); if (execfiles.isEmpty()) { out.println("[WARN] No execution data files provided."); } else { for (final File file : execfiles) { out.printf("[INFO] Loading execution data file %s.%n", file.getAbsolutePath()); loader.load(file); } } return loader; } private IBundleCoverage analyze(final ExecutionDataStore data, final PrintWriter out) throws IOException { final CoverageBuilder builder = new CoverageBuilder(); final Analyzer analyzer = new Analyzer(data, builder); for (final File f : classfiles) { analyzer.analyzeAll(f); } printNoMatchWarning(builder.getNoMatchClasses(), out); return builder.getBundle(name); } private void printNoMatchWarning(final Collection nomatch, final PrintWriter out) { if (!nomatch.isEmpty()) { out.println( "[WARN] Some classes do not match with execution data."); out.println( "[WARN] For report generation the same class files must be used as at runtime."); for (final IClassCoverage c : nomatch) { out.printf( "[WARN] Execution data for class %s does not match.%n", c.getName()); } } } private void writeReports(final IBundleCoverage bundle, final ExecFileLoader loader, final PrintWriter out) throws IOException { out.printf("[INFO] Analyzing %s classes.%n", Integer.valueOf(bundle.getClassCounter().getTotalCount())); final IReportVisitor visitor = createReportVisitor(); visitor.visitInfo(loader.getSessionInfoStore().getInfos(), loader.getExecutionDataStore().getContents()); visitor.visitBundle(bundle, getSourceLocator()); visitor.visitEnd(); } private IReportVisitor createReportVisitor() throws IOException { final List visitors = new ArrayList(); if (xml != null) { final XMLFormatter formatter = new XMLFormatter(); visitors.add(formatter.createVisitor(new FileOutputStream(xml))); } if (csv != null) { final CSVFormatter formatter = new CSVFormatter(); visitors.add(formatter.createVisitor(new FileOutputStream(csv))); } if (html != null) { final HTMLFormatter formatter = new HTMLFormatter(); visitors.add( formatter.createVisitor(new FileMultiReportOutput(html))); } return new MultiReportVisitor(visitors); } private ISourceFileLocator getSourceLocator() { final MultiSourceFileLocator multi = new MultiSourceFileLocator( tabwidth); for (final File f : sourcefiles) { multi.add(new DirectorySourceFileLocator(f, encoding, tabwidth)); } return multi; } } jacoco-0.8.11/org.jacoco.cli/src/org/jacoco/cli/internal/commands/Version.java000066400000000000000000000020121451257705100271230ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.cli.internal.commands; import java.io.IOException; import java.io.PrintWriter; import org.jacoco.cli.internal.Command; import org.jacoco.core.JaCoCo; /** * The version command. */ public class Version extends Command { @Override public String description() { return "Print JaCoCo version information."; } @Override public int execute(final PrintWriter out, final PrintWriter err) throws IOException { out.println(JaCoCo.VERSION); return 0; } } jacoco-0.8.11/org.jacoco.core.test.validation.groovy/000077500000000000000000000000001451257705100224545ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/.classpath000066400000000000000000000013671451257705100244460ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.core.test.validation.groovy/.project000066400000000000000000000013571451257705100241310ustar00rootroot00000000000000 org.jacoco.core.test.validation.groovy org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.jdt.core.javanature org.eclipse.m2e.core.maven2Nature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.core.test.validation.groovy/pom.xml000066400000000000000000000043671451257705100240030ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.core.test.validation 0.8.11 ../org.jacoco.core.test.validation org.jacoco.core.test.validation.groovy JaCoCo :: Test :: Core :: Validation Groovy 3.0.0 3.0.19 ${project.groupId} org.jacoco.core.test org.codehaus.groovy groovy ${groovy.version} org.codehaus.gmavenplus gmavenplus-plugin ${gmaven.version} compile process-sources compile ${groovy.targetBytecode} ${project.build.sourceDirectory} **/*.groovy jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/000077500000000000000000000000001451257705100232435ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/000077500000000000000000000000001451257705100240325ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/000077500000000000000000000000001451257705100252705ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/000077500000000000000000000000001451257705100262205ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/000077500000000000000000000000001451257705100271775ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/000077500000000000000000000000001451257705100313315ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/000077500000000000000000000000001451257705100326565ustar00rootroot00000000000000GroovyAutoCloneClassTest.java000066400000000000000000000020261451257705100403670ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Oliver Nautsch - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.groovy; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.groovy.targets.GroovyAutoCloneClassTarget; import org.junit.Test; /** * Test of class with {@link groovy.transform.AutoClone} annotation. */ public class GroovyAutoCloneClassTest extends ValidationTestBase { public GroovyAutoCloneClassTest() { super(GroovyAutoCloneClassTarget.class); } @Test public void test_method_count() { assertMethodCount(1); } } GroovyAutoExternalizeClassTest.java000066400000000000000000000020461451257705100416230ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Stephan Classen * Vadim Bauer * *******************************************************************************/ package org.jacoco.core.test.validation.groovy; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.groovy.targets.GroovyAutoExternalizeClassTarget; import org.junit.Test; /** * Test of class with {@link groovy.transform.AutoExternalize} annotation. */ public class GroovyAutoExternalizeClassTest extends ValidationTestBase { public GroovyAutoExternalizeClassTest() { super(GroovyAutoExternalizeClassTarget.class); } @Test public void test_method_count() { assertMethodCount(1); } } GroovyBindableClassTest.java000066400000000000000000000017771451257705100402120ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Stephan Classen * Vadim Bauer * *******************************************************************************/ package org.jacoco.core.test.validation.groovy; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.groovy.targets.GroovyBindableClassTarget; import org.junit.Test; /** * Test of class with {@link groovy.beans.Bindable} annotation. */ public class GroovyBindableClassTest extends ValidationTestBase { public GroovyBindableClassTest() { super(GroovyBindableClassTarget.class); } @Test public void test_method_count() { assertMethodCount(1); } } GroovyBuilderClassTest.java000066400000000000000000000020171451257705100400640ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Jan Wloka - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.groovy; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.groovy.targets.GroovyBuilderClassTarget; import org.junit.Test; /** * Test of class with {@link groovy.transform.builder.Builder} annotation. */ public class GroovyBuilderClassTest extends ValidationTestBase { public GroovyBuilderClassTest() { super(GroovyBuilderClassTarget.class); } @Test public void test_method_count() { assertMethodCount(1); } } GroovyCanonicalClassTest.java000066400000000000000000000020261451257705100403650ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Andres Almiray - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.groovy; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.groovy.targets.GroovyCanonicalClassTarget; import org.junit.Test; /** * Test of class with {@link groovy.transform.Canonical} annotation. */ public class GroovyCanonicalClassTest extends ValidationTestBase { public GroovyCanonicalClassTest() { super(GroovyCanonicalClassTarget.class); } @Test public void test_method_count() { assertMethodCount(1); } } GroovyDelegateClassTest.java000066400000000000000000000020171451257705100402100ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Jan Wloka - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.groovy; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.groovy.targets.GroovyDelegateClassTarget; import org.junit.Test; /** * Test of class with field annotated by {@link groovy.lang.Delegate}. */ public class GroovyDelegateClassTest extends ValidationTestBase { public GroovyDelegateClassTest() { super(GroovyDelegateClassTarget.class); } @Test public void test_method_count() { assertMethodCount(4); } } GroovyImmutableClassTest.java000066400000000000000000000020261451257705100404150ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Oliver Nautsch - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.groovy; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.groovy.targets.GroovyImmutableClassTarget; import org.junit.Test; /** * Test of class with {@link groovy.transform.Immutable} annotation. */ public class GroovyImmutableClassTest extends ValidationTestBase { public GroovyImmutableClassTest() { super(GroovyImmutableClassTarget.class); } @Test public void test_method_count() { assertMethodCount(1); } } GroovyIndexPropertyClassTest.java000066400000000000000000000020651451257705100413150ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Stephan Classen * Vadim Bauer * *******************************************************************************/ package org.jacoco.core.test.validation.groovy; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.groovy.targets.GroovyIndexPropertyClassTarget; import org.junit.Test; /** * Test of class with fields annotated by * {@link groovy.transform.IndexedProperty} annotation. */ public class GroovyIndexPropertyClassTest extends ValidationTestBase { public GroovyIndexPropertyClassTest() { super(GroovyIndexPropertyClassTarget.class); } @Test public void test_method_count() { assertMethodCount(1); } } GroovySortableClassTest.java000066400000000000000000000020531451257705100402510ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Stephan Classen * Vadim Bauer * *******************************************************************************/ package org.jacoco.core.test.validation.groovy; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.groovy.targets.GroovySortableClassTarget; import org.junit.Test; /** * Test of class with {@link groovy.transform.Sortable} annotation. */ public class GroovySortableClassTest extends ValidationTestBase { public GroovySortableClassTest() { super(GroovySortableClassTarget.class); } @Test public void test_method_count() { // main method and static initializer assertMethodCount(2); } } GroovyVetoableClassTest.java000066400000000000000000000017771451257705100402530ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Stephan Classen * Vadim Bauer * *******************************************************************************/ package org.jacoco.core.test.validation.groovy; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.groovy.targets.GroovyVetoableClassTarget; import org.junit.Test; /** * Test of class with {@link groovy.beans.Vetoable} annotation. */ public class GroovyVetoableClassTest extends ValidationTestBase { public GroovyVetoableClassTest() { super(GroovyVetoableClassTarget.class); } @Test public void test_method_count() { assertMethodCount(1); } } targets/000077500000000000000000000000001451257705100342505ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovyGroovyAutoCloneClassTarget.groovy000066400000000000000000000014361451257705100427570ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Oliver Nautsch - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.groovy.targets import groovy.transform.AutoClone @AutoClone class GroovyAutoCloneClassTarget { // assertEmpty() static void main(String[] args) { new GroovyAutoCloneClassTarget() // assertFullyCovered() } } GroovyAutoExternalizeClassTarget.groovy000066400000000000000000000016311451257705100442060ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Stephan Classen * Vadim Bauer * *******************************************************************************/ package org.jacoco.core.test.validation.groovy.targets import groovy.transform.AutoExternalize @AutoExternalize class GroovyAutoExternalizeClassTarget { // assertEmpty() String first // assertEmpty() List favItems // assertEmpty() Date since // assertEmpty() static void main(String[] args) { new GroovyAutoExternalizeClassTarget() // assertFullyCovered() } } GroovyBindableClassTarget.groovy000066400000000000000000000015521451257705100425650ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Stephan Classen * Vadim Bauer * *******************************************************************************/ package org.jacoco.core.test.validation.groovy.targets import groovy.beans.Bindable class GroovyBindableClassTarget { // assertEmpty() @Bindable String firstName // assertEmpty() @Bindable def zipCode // assertEmpty() static void main(String[] args) { new GroovyBindableClassTarget() // assertFullyCovered() } } GroovyBuilderClassTarget.groovy000066400000000000000000000016151451257705100424530ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Jan Wloka - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.groovy.targets import groovy.transform.builder.Builder import groovy.transform.builder.SimpleStrategy @Builder(builderStrategy = SimpleStrategy) class GroovyBuilderClassTarget { // assertEmpty() String name // assertEmpty() static void main(String[] args) { new GroovyBuilderClassTarget() // assertFullyCovered() } } GroovyCanonicalClassTarget.groovy000066400000000000000000000015011451257705100427460ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Andres Almiray - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.groovy.targets import groovy.transform.Canonical @Canonical class GroovyCanonicalClassTarget { // assertEmpty() int valRead // assertEmpty() static void main(String[] args) { new GroovyCanonicalClassTarget() // assertFullyCovered() } } GroovyDelegateClassTarget.groovy000066400000000000000000000020141451257705100425710ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Jan Wloka - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.groovy.targets class GroovyDelegateClassTarget { // assertEmpty() static class D { void m1() { } // assertFullyCovered() void m2() { } // assertFullyCovered() } @Delegate D delegate = new D() // assertEmpty() void m2() { delegate.m2() // assertFullyCovered() } static void main(String[] args) { new GroovyDelegateClassTarget().m1() new GroovyDelegateClassTarget().m2() } } GroovyImmutableClassTarget.groovy000066400000000000000000000015421451257705100430030ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Oliver Nautsch - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.groovy.targets import groovy.transform.Immutable @Immutable class GroovyImmutableClassTarget { // assertEmpty() String name // assertEmpty() int age // assertEmpty() static void main(String[] args) { new GroovyImmutableClassTarget() // assertFullyCovered() } } GroovyIndexPropertyClassTarget.groovy000066400000000000000000000017531451257705100437040ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Stephan Classen * Vadim Bauer * *******************************************************************************/ package org.jacoco.core.test.validation.groovy.targets import groovy.io.FileType import groovy.transform.IndexedProperty class GroovyIndexPropertyClassTarget { // assertEmpty() @IndexedProperty FileType[] someField // assertEmpty() @IndexedProperty List otherField // assertEmpty() @IndexedProperty List furtherField // assertEmpty() static void main(String[] args) { new GroovyIndexPropertyClassTarget() // assertFullyCovered() } } GroovySortableClassTarget.groovy000066400000000000000000000015751451257705100426450ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Stephan Classen * Vadim Bauer * *******************************************************************************/ package org.jacoco.core.test.validation.groovy.targets import groovy.transform.Sortable @Sortable class GroovySortableClassTarget { // assertEmpty() String first // assertEmpty() String last // assertEmpty() Integer born // assertEmpty() static void main(String[] args) { new GroovySortableClassTarget() // assertFullyCovered() } } GroovyVetoableClassTarget.groovy000066400000000000000000000015271451257705100426300ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.groovy/src/org/jacoco/core/test/validation/groovy/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Stephan Classen * Vadim Bauer * *******************************************************************************/ package org.jacoco.core.test.validation.groovy.targets import groovy.beans.Vetoable @Vetoable class GroovyVetoableClassTarget { // assertEmpty() String firstName // assertEmpty() def zipCode // assertEmpty() static void main(String[] args) { new GroovyVetoableClassTarget() // assertFullyCovered() } } jacoco-0.8.11/org.jacoco.core.test.validation.java14/000077500000000000000000000000001451257705100222155ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java14/.classpath000066400000000000000000000013701451257705100242010ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.core.test.validation.java14/.project000066400000000000000000000013571451257705100236720ustar00rootroot00000000000000 org.jacoco.core.test.validation.java14 org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.core.test.validation.java14/pom.xml000066400000000000000000000023441451257705100235350ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.core.test.validation 0.8.11 ../org.jacoco.core.test.validation org.jacoco.core.test.validation.java14 JaCoCo :: Test :: Core :: Validation Java 14 14 ${project.groupId} org.jacoco.core.test jacoco-0.8.11/org.jacoco.core.test.validation.java14/src/000077500000000000000000000000001451257705100230045ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java14/src/org/000077500000000000000000000000001451257705100235735ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java14/src/org/jacoco/000077500000000000000000000000001451257705100250315ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java14/src/org/jacoco/core/000077500000000000000000000000001451257705100257615ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java14/src/org/jacoco/core/test/000077500000000000000000000000001451257705100267405ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java14/src/org/jacoco/core/test/validation/000077500000000000000000000000001451257705100310725ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java14/src/org/jacoco/core/test/validation/java14/000077500000000000000000000000001451257705100321605ustar00rootroot00000000000000SwitchExpressionsTest.java000066400000000000000000000017211451257705100373110ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java14/src/org/jacoco/core/test/validation/java14/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java14; import org.jacoco.core.test.validation.Source.Line; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java14.targets.SwitchExpressionsTarget; /** * Test of code coverage for switch expressions. */ public class SwitchExpressionsTest extends ValidationTestBase { public SwitchExpressionsTest() { super(SwitchExpressionsTarget.class); } } targets/000077500000000000000000000000001451257705100335525ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java14/src/org/jacoco/core/test/validation/java14SwitchExpressionsTarget.java000066400000000000000000000056261451257705100413010ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java14/src/org/jacoco/core/test/validation/java14/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java14.targets; import static org.jacoco.core.test.validation.targets.Stubs.i1; import static org.jacoco.core.test.validation.targets.Stubs.i2; import static org.jacoco.core.test.validation.targets.Stubs.nop; import org.jacoco.core.test.validation.targets.Stubs; /** * This target exercises switch expressions. */ public class SwitchExpressionsTarget { public static void main(String[] args) { switchExpressionWithArrows(); multiValueSwitchExpressionWithArrows(); switchExpressionWithArrowsAndYield(); switchExpressionWithYield(); exhaustiveSwitchExpression(Stubs.Enum.A); exhaustiveSwitchExpression(Stubs.Enum.B); exhaustiveSwitchExpression(Stubs.Enum.C); } private static void switchExpressionWithArrows() { nop(switch (i2()) { // assertFullyCovered(3, 1) case 1 -> i1(); // assertNotCovered() case 2 -> i1(); // assertFullyCovered() case 3 -> i1(); // assertNotCovered() default -> i1(); // assertNotCovered() }); } private static void multiValueSwitchExpressionWithArrows() { nop(switch (i2()) { // assertFullyCovered(2, 1) case 1, 2 -> i1(); // assertFullyCovered() case 3, 4 -> i1(); // assertNotCovered() default -> i1(); // assertNotCovered() }); } private static void switchExpressionWithArrowsAndYield() { nop(switch (i2()) { // assertFullyCovered(3, 1) case 1 -> { nop(); // assertNotCovered() yield i1(); // assertNotCovered() } case 2 -> { nop(); // assertFullyCovered() yield i1(); // assertFullyCovered() } case 3 -> { nop(); // assertNotCovered() yield i1(); // assertNotCovered() } default -> { nop(); // assertNotCovered() yield i1(); // assertNotCovered() } }); } private static void switchExpressionWithYield() { nop(switch (i2()) { // assertFullyCovered(3, 1) case 1: nop(); // assertNotCovered() yield i1(); // assertNotCovered() case 2: nop(); // assertFullyCovered() yield i1(); // assertFullyCovered() case 3: nop(); // assertNotCovered() yield i1(); // assertNotCovered() default: nop(); // assertNotCovered() yield i1(); // assertNotCovered() }); } private static void exhaustiveSwitchExpression(Stubs.Enum e) { nop(switch (e) { // assertFullyCovered(0, 3) case A -> i1(); // assertFullyCovered() case B -> i1(); // assertFullyCovered() case C -> i1(); // assertFullyCovered() }); // assertEmpty() } } jacoco-0.8.11/org.jacoco.core.test.validation.java16/000077500000000000000000000000001451257705100222175ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java16/.classpath000066400000000000000000000013701451257705100242030ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.core.test.validation.java16/.project000066400000000000000000000013571451257705100236740ustar00rootroot00000000000000 org.jacoco.core.test.validation.java16 org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.core.test.validation.java16/pom.xml000066400000000000000000000024201451257705100235320ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.core.test.validation 0.8.11 ../org.jacoco.core.test.validation org.jacoco.core.test.validation.java16 JaCoCo :: Test :: Core :: Validation Java 16 16 ${project.groupId} org.jacoco.core.test ${project.version} jacoco-0.8.11/org.jacoco.core.test.validation.java16/src/000077500000000000000000000000001451257705100230065ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java16/src/org/000077500000000000000000000000001451257705100235755ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java16/src/org/jacoco/000077500000000000000000000000001451257705100250335ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java16/src/org/jacoco/core/000077500000000000000000000000001451257705100257635ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java16/src/org/jacoco/core/test/000077500000000000000000000000001451257705100267425ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java16/src/org/jacoco/core/test/validation/000077500000000000000000000000001451257705100310745ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java16/src/org/jacoco/core/test/validation/java16/000077500000000000000000000000001451257705100321645ustar00rootroot00000000000000InstanceofTest.java000066400000000000000000000016721451257705100357070ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java16/src/org/jacoco/core/test/validation/java16/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java16; import org.jacoco.core.test.validation.Source.Line; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java16.targets.InstanceofTarget; /** * Test of code coverage in {@link InstanceofTarget}. */ public class InstanceofTest extends ValidationTestBase { public InstanceofTest() { super(InstanceofTarget.class); } } RecordsTest.java000066400000000000000000000015521451257705100352140ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java16/src/org/jacoco/core/test/validation/java16/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java16; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java16.targets.RecordsTarget; /** * Test of code coverage for records. */ public class RecordsTest extends ValidationTestBase { public RecordsTest() { super(RecordsTarget.class); } } targets/000077500000000000000000000000001451257705100335565ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java16/src/org/jacoco/core/test/validation/java16InstanceofTarget.java000066400000000000000000000020261451257705100376610ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java16/src/org/jacoco/core/test/validation/java16/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java16.targets; import static org.jacoco.core.test.validation.targets.Stubs.nop; /** * This target exercises pattern matching for instanceof * (JEP 394). */ public class InstanceofTarget { private static void ifInstanceof(Object e) { if (e instanceof String s) { // assertFullyCovered(0, 2) nop(s); } } public static void main(String[] args) { ifInstanceof(new Object()); ifInstanceof("string"); } } RecordsTarget.java000066400000000000000000000024451451257705100371760ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java16/src/org/jacoco/core/test/validation/java16/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java16.targets; /** * This target exercises records * (JEP 395). */ public class RecordsTarget { record WithoutFields() { // assertFullyCovered() } record WithFields( // assertFullyCovered() int x // assertEmpty() ) { } record WithCustomMethods(int x) { // assertFullyCovered() public int x() { return x; // assertEmpty() } public String toString() { return ""; // assertNotCovered() } public int hashCode() { return 0; // assertNotCovered() } public boolean equals(Object object) { return false; // assertNotCovered() } } public static void main(String[] args) { new WithoutFields(); new WithFields(42); new WithCustomMethods(42); } } jacoco-0.8.11/org.jacoco.core.test.validation.java21/000077500000000000000000000000001451257705100222135ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java21/.classpath000066400000000000000000000013701451257705100241770ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.core.test.validation.java21/.project000066400000000000000000000013571451257705100236700ustar00rootroot00000000000000 org.jacoco.core.test.validation.java21 org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.core.test.validation.java21/.settings/000077500000000000000000000000001451257705100241315ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java21/.settings/org.eclipse.jdt.core.prefs000066400000000000000000000655131451257705100311250ustar00rootroot00000000000000#Sat Sep 05 17:45:34 CEST 2009 eclipse.preferences.version=1 org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.5 org.eclipse.jdt.core.compiler.compliance=1.5 org.eclipse.jdt.core.compiler.problem.enablePreviewFeatures=enabled org.eclipse.jdt.core.compiler.doc.comment.support=enabled org.eclipse.jdt.core.compiler.problem.annotationSuperInterface=warning org.eclipse.jdt.core.compiler.problem.assertIdentifier=error org.eclipse.jdt.core.compiler.problem.autoboxing=warning org.eclipse.jdt.core.compiler.problem.deprecation=warning org.eclipse.jdt.core.compiler.problem.deprecationInDeprecatedCode=disabled org.eclipse.jdt.core.compiler.problem.deprecationWhenOverridingDeprecatedMethod=disabled org.eclipse.jdt.core.compiler.problem.discouragedReference=warning org.eclipse.jdt.core.compiler.problem.emptyStatement=ignore org.eclipse.jdt.core.compiler.problem.enumIdentifier=error org.eclipse.jdt.core.compiler.problem.fallthroughCase=ignore org.eclipse.jdt.core.compiler.problem.fatalOptionalError=enabled org.eclipse.jdt.core.compiler.problem.fieldHiding=ignore org.eclipse.jdt.core.compiler.problem.finalParameterBound=warning org.eclipse.jdt.core.compiler.problem.finallyBlockNotCompletingNormally=warning org.eclipse.jdt.core.compiler.problem.forbiddenReference=error org.eclipse.jdt.core.compiler.problem.hiddenCatchBlock=warning org.eclipse.jdt.core.compiler.problem.incompatibleNonInheritedInterfaceMethod=warning org.eclipse.jdt.core.compiler.problem.incompleteEnumSwitch=ignore org.eclipse.jdt.core.compiler.problem.indirectStaticAccess=ignore org.eclipse.jdt.core.compiler.problem.invalidJavadoc=warning org.eclipse.jdt.core.compiler.problem.invalidJavadocTags=enabled org.eclipse.jdt.core.compiler.problem.invalidJavadocTagsDeprecatedRef=disabled org.eclipse.jdt.core.compiler.problem.invalidJavadocTagsNotVisibleRef=enabled org.eclipse.jdt.core.compiler.problem.invalidJavadocTagsVisibility=public org.eclipse.jdt.core.compiler.problem.localVariableHiding=ignore org.eclipse.jdt.core.compiler.problem.methodWithConstructorName=warning org.eclipse.jdt.core.compiler.problem.missingDeprecatedAnnotation=ignore org.eclipse.jdt.core.compiler.problem.missingJavadocComments=warning org.eclipse.jdt.core.compiler.problem.missingJavadocCommentsOverriding=disabled org.eclipse.jdt.core.compiler.problem.missingJavadocCommentsVisibility=protected org.eclipse.jdt.core.compiler.problem.missingJavadocTagDescription=no_tag org.eclipse.jdt.core.compiler.problem.missingJavadocTags=warning org.eclipse.jdt.core.compiler.problem.missingJavadocTagsOverriding=disabled org.eclipse.jdt.core.compiler.problem.missingJavadocTagsVisibility=protected org.eclipse.jdt.core.compiler.problem.missingOverrideAnnotation=error org.eclipse.jdt.core.compiler.problem.missingSerialVersion=warning org.eclipse.jdt.core.compiler.problem.noEffectAssignment=warning org.eclipse.jdt.core.compiler.problem.noImplicitStringConversion=warning org.eclipse.jdt.core.compiler.problem.nonExternalizedStringLiteral=ignore org.eclipse.jdt.core.compiler.problem.nullReference=warning org.eclipse.jdt.core.compiler.problem.overridingPackageDefaultMethod=warning org.eclipse.jdt.core.compiler.problem.parameterAssignment=ignore org.eclipse.jdt.core.compiler.problem.possibleAccidentalBooleanAssignment=ignore org.eclipse.jdt.core.compiler.problem.potentialNullReference=ignore org.eclipse.jdt.core.compiler.problem.rawTypeReference=warning org.eclipse.jdt.core.compiler.problem.redundantNullCheck=ignore org.eclipse.jdt.core.compiler.problem.redundantSuperinterface=ignore org.eclipse.jdt.core.compiler.problem.specialParameterHidingField=disabled org.eclipse.jdt.core.compiler.problem.staticAccessReceiver=warning org.eclipse.jdt.core.compiler.problem.suppressWarnings=enabled org.eclipse.jdt.core.compiler.problem.syntheticAccessEmulation=ignore org.eclipse.jdt.core.compiler.problem.typeParameterHiding=warning org.eclipse.jdt.core.compiler.problem.uncheckedTypeOperation=warning org.eclipse.jdt.core.compiler.problem.undocumentedEmptyBlock=ignore org.eclipse.jdt.core.compiler.problem.unhandledWarningToken=warning org.eclipse.jdt.core.compiler.problem.unnecessaryElse=ignore org.eclipse.jdt.core.compiler.problem.unnecessaryTypeCheck=ignore org.eclipse.jdt.core.compiler.problem.unqualifiedFieldAccess=ignore org.eclipse.jdt.core.compiler.problem.unusedDeclaredThrownException=ignore org.eclipse.jdt.core.compiler.problem.unusedDeclaredThrownExceptionExemptExceptionAndThrowable=enabled org.eclipse.jdt.core.compiler.problem.unusedDeclaredThrownExceptionIncludeDocCommentReference=enabled org.eclipse.jdt.core.compiler.problem.unusedDeclaredThrownExceptionWhenOverriding=disabled org.eclipse.jdt.core.compiler.problem.unusedImport=warning org.eclipse.jdt.core.compiler.problem.unusedLabel=warning org.eclipse.jdt.core.compiler.problem.unusedLocal=warning org.eclipse.jdt.core.compiler.problem.unusedParameter=warning org.eclipse.jdt.core.compiler.problem.unusedParameterIncludeDocCommentReference=disabled org.eclipse.jdt.core.compiler.problem.unusedParameterWhenImplementingAbstract=disabled org.eclipse.jdt.core.compiler.problem.unusedParameterWhenOverridingConcrete=disabled org.eclipse.jdt.core.compiler.problem.unusedPrivateMember=warning org.eclipse.jdt.core.compiler.problem.unusedWarningToken=warning org.eclipse.jdt.core.compiler.problem.varargsArgumentNeedCast=warning org.eclipse.jdt.core.compiler.source=1.5 org.eclipse.jdt.core.formatter.align_type_members_on_columns=false org.eclipse.jdt.core.formatter.alignment_for_arguments_in_allocation_expression=16 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_enum_constant=16 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_explicit_constructor_call=16 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_method_invocation=16 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_qualified_allocation_expression=16 org.eclipse.jdt.core.formatter.alignment_for_assignment=0 org.eclipse.jdt.core.formatter.alignment_for_binary_expression=16 org.eclipse.jdt.core.formatter.alignment_for_compact_if=16 org.eclipse.jdt.core.formatter.alignment_for_conditional_expression=80 org.eclipse.jdt.core.formatter.alignment_for_enum_constants=0 org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer=16 org.eclipse.jdt.core.formatter.alignment_for_multiple_fields=16 org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_parameters_in_method_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_selector_in_method_invocation=16 org.eclipse.jdt.core.formatter.alignment_for_superclass_in_type_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_enum_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_type_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_constructor_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_method_declaration=16 org.eclipse.jdt.core.formatter.blank_lines_after_imports=1 org.eclipse.jdt.core.formatter.blank_lines_after_package=1 org.eclipse.jdt.core.formatter.blank_lines_before_field=0 org.eclipse.jdt.core.formatter.blank_lines_before_first_class_body_declaration=0 org.eclipse.jdt.core.formatter.blank_lines_before_imports=1 org.eclipse.jdt.core.formatter.blank_lines_before_member_type=1 org.eclipse.jdt.core.formatter.blank_lines_before_method=1 org.eclipse.jdt.core.formatter.blank_lines_before_new_chunk=1 org.eclipse.jdt.core.formatter.blank_lines_before_package=0 org.eclipse.jdt.core.formatter.blank_lines_between_import_groups=1 org.eclipse.jdt.core.formatter.blank_lines_between_type_declarations=1 org.eclipse.jdt.core.formatter.brace_position_for_annotation_type_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_anonymous_type_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_array_initializer=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_block=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_block_in_case=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_constructor_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_enum_constant=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_enum_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_method_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_switch=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_type_declaration=end_of_line org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_block_comment=false org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_javadoc_comment=false org.eclipse.jdt.core.formatter.comment.format_block_comments=true org.eclipse.jdt.core.formatter.comment.format_header=false org.eclipse.jdt.core.formatter.comment.format_html=true org.eclipse.jdt.core.formatter.comment.format_javadoc_comments=true org.eclipse.jdt.core.formatter.comment.format_line_comments=true org.eclipse.jdt.core.formatter.comment.format_source_code=true org.eclipse.jdt.core.formatter.comment.indent_parameter_description=true org.eclipse.jdt.core.formatter.comment.indent_root_tags=true org.eclipse.jdt.core.formatter.comment.insert_new_line_before_root_tags=insert org.eclipse.jdt.core.formatter.comment.insert_new_line_for_parameter=insert org.eclipse.jdt.core.formatter.comment.line_length=80 org.eclipse.jdt.core.formatter.compact_else_if=true org.eclipse.jdt.core.formatter.continuation_indentation=2 org.eclipse.jdt.core.formatter.continuation_indentation_for_array_initializer=2 org.eclipse.jdt.core.formatter.format_guardian_clause_on_one_line=false org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_annotation_declaration_header=true org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_constant_header=true org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_declaration_header=true org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_type_header=true org.eclipse.jdt.core.formatter.indent_breaks_compare_to_cases=true org.eclipse.jdt.core.formatter.indent_empty_lines=false org.eclipse.jdt.core.formatter.indent_statements_compare_to_block=true org.eclipse.jdt.core.formatter.indent_statements_compare_to_body=true org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_cases=true org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_switch=false org.eclipse.jdt.core.formatter.indentation.size=4 org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_local_variable=insert org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_member=insert org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_parameter=do not insert org.eclipse.jdt.core.formatter.insert_new_line_after_opening_brace_in_array_initializer=do not insert org.eclipse.jdt.core.formatter.insert_new_line_at_end_of_file_if_missing=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_catch_in_try_statement=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_closing_brace_in_array_initializer=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_else_in_if_statement=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_finally_in_try_statement=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_while_in_do_statement=do not insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_annotation_declaration=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_anonymous_type_declaration=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_block=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_constant=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_declaration=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_method_body=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_after_and_in_type_parameter=insert org.eclipse.jdt.core.formatter.insert_space_after_assignment_operator=insert org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation_type_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_after_binary_operator=insert org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_parameters=insert org.eclipse.jdt.core.formatter.insert_space_after_closing_brace_in_block=insert org.eclipse.jdt.core.formatter.insert_space_after_closing_paren_in_cast=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_assert=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_case=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_conditional=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_for=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_labeled_statement=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_allocation_expression=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_annotation=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_array_initializer=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_parameters=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_throws=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_constant_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_declarations=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_explicitconstructorcall_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_increments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_inits=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_parameters=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_throws=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_invocation_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_field_declarations=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_local_declarations=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_parameterized_type_reference=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_superinterfaces=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_parameters=insert org.eclipse.jdt.core.formatter.insert_space_after_ellipsis=insert org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_parameterized_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_brace_in_array_initializer=insert org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_cast=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_catch=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_constructor_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_enum_constant=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_for=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_if=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_invocation=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_parenthesized_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_switch=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_synchronized=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_while=do not insert org.eclipse.jdt.core.formatter.insert_space_after_postfix_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_after_prefix_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_after_question_in_conditional=insert org.eclipse.jdt.core.formatter.insert_space_after_question_in_wildcard=do not insert org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_for=insert org.eclipse.jdt.core.formatter.insert_space_after_unary_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_before_and_in_type_parameter=insert org.eclipse.jdt.core.formatter.insert_space_before_assignment_operator=insert org.eclipse.jdt.core.formatter.insert_space_before_at_in_annotation_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_binary_operator=insert org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_parameterized_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_brace_in_array_initializer=insert org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_cast=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_catch=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_constructor_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_enum_constant=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_for=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_if=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_invocation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_parenthesized_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_switch=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_synchronized=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_while=do not insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_assert=insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_case=do not insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_conditional=insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_default=do not insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_for=insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_labeled_statement=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_array_initializer=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_throws=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_constant_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_declarations=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_explicitconstructorcall_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_increments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_inits=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_throws=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_invocation_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_field_declarations=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_local_declarations=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_parameterized_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_superinterfaces=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_ellipsis=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_parameterized_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_annotation_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_anonymous_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_array_initializer=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_block=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_constructor_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_constant=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_method_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_switch=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation_type_member_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_catch=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_constructor_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_enum_constant=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_for=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_if=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_invocation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_parenthesized_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_switch=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_synchronized=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_while=insert org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_return=insert org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_throw=insert org.eclipse.jdt.core.formatter.insert_space_before_postfix_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_before_prefix_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_before_question_in_conditional=insert org.eclipse.jdt.core.formatter.insert_space_before_question_in_wildcard=do not insert org.eclipse.jdt.core.formatter.insert_space_before_semicolon=do not insert org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_for=do not insert org.eclipse.jdt.core.formatter.insert_space_before_unary_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_between_brackets_in_array_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_braces_in_array_initializer=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_brackets_in_array_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_annotation_type_member_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_constructor_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_enum_constant=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_invocation=do not insert org.eclipse.jdt.core.formatter.keep_else_statement_on_same_line=false org.eclipse.jdt.core.formatter.keep_empty_array_initializer_on_one_line=false org.eclipse.jdt.core.formatter.keep_imple_if_on_one_line=false org.eclipse.jdt.core.formatter.keep_then_statement_on_same_line=false org.eclipse.jdt.core.formatter.lineSplit=80 org.eclipse.jdt.core.formatter.never_indent_block_comments_on_first_column=false org.eclipse.jdt.core.formatter.never_indent_line_comments_on_first_column=false org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_method_body=0 org.eclipse.jdt.core.formatter.number_of_empty_lines_to_preserve=1 org.eclipse.jdt.core.formatter.put_empty_statement_on_new_line=true org.eclipse.jdt.core.formatter.tabulation.char=tab org.eclipse.jdt.core.formatter.tabulation.size=4 org.eclipse.jdt.core.formatter.use_tabs_only_for_leading_indentations=false org.eclipse.jdt.core.formatter.wrap_before_binary_operator=true jacoco-0.8.11/org.jacoco.core.test.validation.java21/pom.xml000066400000000000000000000040701451257705100235310ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.core.test.validation 0.8.11 ../org.jacoco.core.test.validation org.jacoco.core.test.validation.java21 JaCoCo :: Test :: Core :: Validation Java 21 21 ${project.groupId} org.jacoco.core.test ${project.version} com.diffplug.spotless spotless-maven-plugin ../org.jacoco.core.test.validation.java21/.settings/org.eclipse.jdt.core.prefs jacoco-0.8.11/org.jacoco.core.test.validation.java21/src/000077500000000000000000000000001451257705100230025ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java21/src/org/000077500000000000000000000000001451257705100235715ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java21/src/org/jacoco/000077500000000000000000000000001451257705100250275ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java21/src/org/jacoco/core/000077500000000000000000000000001451257705100257575ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java21/src/org/jacoco/core/test/000077500000000000000000000000001451257705100267365ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java21/src/org/jacoco/core/test/validation/000077500000000000000000000000001451257705100310705ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java21/src/org/jacoco/core/test/validation/java21/000077500000000000000000000000001451257705100321545ustar00rootroot00000000000000RecordPatternsTest.java000066400000000000000000000020021451257705100365310ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java21/src/org/jacoco/core/test/validation/java21/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java21; import org.jacoco.core.test.validation.JavaVersion; import org.jacoco.core.test.validation.Source.Line; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java21.targets.RecordPatternsTarget; /** * Test of code coverage in {@link RecordPatternsTarget}. */ public class RecordPatternsTest extends ValidationTestBase { public RecordPatternsTest() { super(RecordPatternsTarget.class); } } SwitchPatternMatchingTest.java000066400000000000000000000016751451257705100400630ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java21/src/org/jacoco/core/test/validation/java21/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java21; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java21.targets.SwitchPatternMatchingTarget; /** * Test of code coverage in {@link SwitchPatternMatchingTarget}. */ public class SwitchPatternMatchingTest extends ValidationTestBase { public SwitchPatternMatchingTest() { super(SwitchPatternMatchingTarget.class); } } targets/000077500000000000000000000000001451257705100335465ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java21/src/org/jacoco/core/test/validation/java21RecordPatternsTarget.java000066400000000000000000000026511451257705100405230ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java21/src/org/jacoco/core/test/validation/java21/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java21.targets; import static org.jacoco.core.test.validation.targets.Stubs.nop; /** * This target exercises Record Patterns * (JEP 440). */ public class RecordPatternsTarget { private record Point(int x, int y) { } private static void instanceofOperator(Object o) { if (o instanceof Point(int x, int y)) { // assertFullyCovered(0, 2) nop(x + y); // assertFullyCovered() } // assertEmpty() } private static void switchStatement(Object p) { switch (p) { // assertFullyCovered(0, 2) case Point(int x, int y) -> nop(x + y); // assertFullyCovered() default -> nop(); // assertFullyCovered() } // assertEmpty() } public static void main(String[] args) { instanceofOperator(new Point(1, 2)); instanceofOperator(new Object()); switchStatement(new Point(1, 2)); switchStatement(new Object()); } } SwitchPatternMatchingTarget.java000066400000000000000000000023221451257705100420310ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java21/src/org/jacoco/core/test/validation/java21/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java21.targets; import static org.jacoco.core.test.validation.targets.Stubs.nop; /** * This target exercises pattern matching for switch * (JEP 441). */ public class SwitchPatternMatchingTarget { private static void example(Object o) { switch (o) { // assertFullyCovered(1, 2) case String s when s.length() == 0 -> // assertFullyCovered(0, 2) nop(s); // assertFullyCovered() case String s -> // assertFullyCovered() nop(s); // assertFullyCovered() default -> // assertEmpty() nop(); // assertNotCovered() } } public static void main(String[] args) { example(""); example("a"); } } jacoco-0.8.11/org.jacoco.core.test.validation.java5/000077500000000000000000000000001451257705100221355ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/.classpath000066400000000000000000000013671451257705100241270ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.core.test.validation.java5/.project000066400000000000000000000013561451257705100236110ustar00rootroot00000000000000 org.jacoco.core.test.validation.java5 org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.core.test.validation.java5/pom.xml000066400000000000000000000022251451257705100234530ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.core.test.validation 0.8.11 ../org.jacoco.core.test.validation org.jacoco.core.test.validation.java5 JaCoCo :: Test :: Core :: Validation Java 5 ${project.groupId} org.jacoco.core.test jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/000077500000000000000000000000001451257705100227245ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/000077500000000000000000000000001451257705100235135ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/000077500000000000000000000000001451257705100247515ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/000077500000000000000000000000001451257705100257015ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/000077500000000000000000000000001451257705100266605ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/000077500000000000000000000000001451257705100310125ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/000077500000000000000000000000001451257705100320205ustar00rootroot00000000000000AnnotationGeneratedTest.java000066400000000000000000000015521451257705100374000ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.AnnotationGeneratedTarget; public class AnnotationGeneratedTest extends ValidationTestBase { public AnnotationGeneratedTest() { super(AnnotationGeneratedTarget.class); } } AnnotationInitializerTest.java000066400000000000000000000026011451257705100377610ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import static org.junit.Assert.assertEquals; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.AnnotationInitializerTarget; /** * Test of initializer in annotations. */ public class AnnotationInitializerTest extends ValidationTestBase { public AnnotationInitializerTest() { super(AnnotationInitializerTarget.class); } @Override protected void run(Class targetClass) throws Exception { // Instrumentation should not add members, // otherwise sun.reflect.annotation.AnnotationInvocationHandler // can throw java.lang.annotation.AnnotationFormatError assertEquals(1, targetClass.getDeclaredFields().length); assertEquals(1, targetClass.getDeclaredMethods().length); // Force initialization targetClass.getField("CONST").get(null); } } AssertTest.java000066400000000000000000000015601451257705100347070ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.AssertTarget; /** * Test of code coverage in {@link AssertTarget}. */ public class AssertTest extends ValidationTestBase { public AssertTest() { super(AssertTarget.class); } } BadCycleClassTest.java000066400000000000000000000022661451257705100361060ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.BadCycleClassTarget; import org.junit.Test; /** * Test of "bad cycles" with classes. */ public class BadCycleClassTest extends ValidationTestBase { public BadCycleClassTest() throws Exception { super(BadCycleClassTarget.class); } @Test public void method_execution_sequence() throws Exception { // The cycle causes a constructor and instance method to be called // before the static initializer of a class: assertLogEvents("childinit", "childsomeMethod", "childclinit", "childinit"); } } BooleanExpressionsTest.java000066400000000000000000000016321451257705100372700ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.BooleanExpressionsTarget; /** * Tests of basic Java boolean expressions. */ public class BooleanExpressionsTest extends ValidationTestBase { public BooleanExpressionsTest() { super(BooleanExpressionsTarget.class); } } ClassInitializerTest.java000066400000000000000000000016211451257705100367150ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.ClassInitializerTarget; /** * Tests of static initializer in classes. */ public class ClassInitializerTest extends ValidationTestBase { public ClassInitializerTest() { super(ClassInitializerTarget.class); } } ConstructorsTest.java000066400000000000000000000016711451257705100361610ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.ConstructorsTarget; /** * Tests for different constructors. Private empty constructors without * arguments are filtered. */ public class ConstructorsTest extends ValidationTestBase { public ConstructorsTest() { super(ConstructorsTarget.class); } } ControlStructureBeforeSuperConstructorTest.java000066400000000000000000000017651451257705100434260ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.ControlStructureBeforeSuperConstructorTarget; /** * Test of probes before the super constructor call. */ public class ControlStructureBeforeSuperConstructorTest extends ValidationTestBase { public ControlStructureBeforeSuperConstructorTest() { super(ControlStructureBeforeSuperConstructorTarget.class); } } ControlStructuresTest.java000066400000000000000000000016251451257705100371740ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.ControlStructuresTarget; /** * Tests of basic Java control structures. */ public class ControlStructuresTest extends ValidationTestBase { public ControlStructuresTest() { super(ControlStructuresTarget.class); } } CyclomaticComplexityTest.java000066400000000000000000000160251451257705100376150ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import static org.jacoco.core.test.validation.targets.Stubs.nop; import static org.junit.Assert.assertEquals; import java.io.IOException; import java.util.Collection; import org.jacoco.core.analysis.Analyzer; import org.jacoco.core.analysis.CoverageBuilder; import org.jacoco.core.analysis.IClassCoverage; import org.jacoco.core.analysis.ICounter; import org.jacoco.core.analysis.IMethodCoverage; import org.jacoco.core.data.ExecutionDataStore; import org.jacoco.core.data.SessionInfoStore; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.internal.analysis.CounterImpl; import org.jacoco.core.runtime.IRuntime; import org.jacoco.core.runtime.RuntimeData; import org.jacoco.core.runtime.SystemPropertiesRuntime; import org.jacoco.core.test.TargetLoader; import org.junit.After; import org.junit.Before; import org.junit.Test; /** * Various tests for cyclomatic complexity of methods. */ public class CyclomaticComplexityTest { public interface Target { public void test(int arg); } private RuntimeData data; private IRuntime runtime; private byte[] bytes; private Target target; @Before public void setup() throws Exception { data = new RuntimeData(); runtime = new SystemPropertiesRuntime(); runtime.startup(data); } @After public void teardown() { runtime.shutdown(); } public static class Simple implements Target { public void test(int arg) { nop(); nop(); nop(); } } @Test public void testSimple1() throws Exception { instrument(Simple.class); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(1, 0), complexity); } @Test public void testSimple2() throws Exception { instrument(Simple.class); target.test(0); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(0, 1), complexity); } public static class If implements Target { public void test(int arg) { if (arg == 0) { nop(); } } } @Test public void testIf1() throws Exception { instrument(If.class); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(2, 0), complexity); } @Test public void testIf2() throws Exception { instrument(If.class); target.test(0); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(1, 1), complexity); } @Test public void testIf3() throws Exception { instrument(If.class); target.test(0); target.test(1); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(0, 2), complexity); } public static class TwoIf implements Target { public void test(int arg) { if (arg < 0) { nop(); } if (arg > 0) { nop(); } } } @Test public void testTwoIf1() throws Exception { instrument(TwoIf.class); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(3, 0), complexity); } @Test public void testTwoIf2() throws Exception { instrument(TwoIf.class); target.test(-1); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(2, 1), complexity); } @Test public void testTwoIf3() throws Exception { instrument(TwoIf.class); target.test(-1); target.test(0); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(1, 2), complexity); } @Test public void testTwoIf4() throws Exception { instrument(TwoIf.class); target.test(-1); target.test(+1); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(0, 3), complexity); } public static class NestedIf implements Target { public void test(int arg) { if (arg >= 0) { if (arg == 0) { nop(); } nop(); } } } @Test public void testNestedIf1() throws Exception { instrument(NestedIf.class); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(3, 0), complexity); } @Test public void testNestedIf2() throws Exception { instrument(NestedIf.class); target.test(-1); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(2, 1), complexity); } @Test public void testNestedIf3() throws Exception { instrument(NestedIf.class); target.test(-1); target.test(0); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(1, 2), complexity); } @Test public void testNestedIf4() throws Exception { instrument(NestedIf.class); target.test(-1); target.test(0); target.test(+1); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(0, 3), complexity); } public static class Switch implements Target { public void test(int arg) { switch (arg) { case 1: nop(); break; case 2: nop(); break; } } } @Test public void testSwitch1() throws Exception { instrument(Switch.class); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(3, 0), complexity); } @Test public void testSwitch2() throws Exception { instrument(Switch.class); target.test(0); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(2, 1), complexity); } @Test public void testSwitch3() throws Exception { instrument(Switch.class); target.test(0); target.test(1); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(1, 2), complexity); } @Test public void testSwitch4() throws Exception { instrument(Switch.class); target.test(0); target.test(1); target.test(2); final ICounter complexity = analyze(); assertEquals(CounterImpl.getInstance(0, 3), complexity); } private void instrument(final Class clazz) throws Exception { bytes = TargetLoader.getClassDataAsBytes(clazz); final byte[] instrumented = new Instrumenter(runtime).instrument(bytes, "TestTarget"); final TargetLoader loader = new TargetLoader(); target = (Target) loader.add(clazz, instrumented).newInstance(); } private ICounter analyze() throws IOException { final CoverageBuilder builder = new CoverageBuilder(); final ExecutionDataStore store = new ExecutionDataStore(); data.collect(store, new SessionInfoStore(), false); final Analyzer analyzer = new Analyzer(store, builder); analyzer.analyzeClass(bytes, "TestTarget"); final Collection classes = builder.getClasses(); assertEquals(1, classes.size(), 0.0); final IClassCoverage classCoverage = classes.iterator().next(); for (final IMethodCoverage m : classCoverage.getMethods()) { if (m.getName().equals("test")) { return m.getComplexityCounter(); } } throw new AssertionError("No test() method."); } } EnumConstructorTest.java000066400000000000000000000016151451257705100366210ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.EnumConstructorTarget; /** * Test of filtering of enum constructors. */ public class EnumConstructorTest extends ValidationTestBase { public EnumConstructorTest() { super(EnumConstructorTarget.class); } } EnumImplicitMethodsTest.java000066400000000000000000000020171451257705100373670ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.EnumImplicitMethodsTarget; import org.junit.Test; /** * Test of an implicit methods and static initializer in enums. */ public class EnumImplicitMethodsTest extends ValidationTestBase { public EnumImplicitMethodsTest() { super(EnumImplicitMethodsTarget.class); } @Test public void test_method_count() { assertMethodCount(5); } } EnumSwitchTest.java000066400000000000000000000025101451257705100355300ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.JavaVersion; import org.jacoco.core.test.validation.Source.Line; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.EnumSwitchTarget; /** * Test of filtering of a synthetic class that is generated by javac for a enum * in switch statement. */ public class EnumSwitchTest extends ValidationTestBase { public EnumSwitchTest() { super(EnumSwitchTarget.class); } public void assertSwitch(final Line line) { if (isJDKCompiler && JavaVersion.current().isBefore("1.6")) { // class that holds "switch map" is not marked as synthetic when // compiling with javac 1.5 assertPartlyCovered(line, 0, 2); } else { assertFullyCovered(line, 0, 2); } } } ExceptionsTest.java000066400000000000000000000037461451257705100355770ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.Source.Line; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.ExceptionsTarget; /** * Tests of exception based control flow. */ public class ExceptionsTest extends ValidationTestBase { public ExceptionsTest() { super(ExceptionsTarget.class); } public void assertCatchNoException(final Line line) { if (isJDKCompiler) { assertNotCovered(line); } else { assertPartlyCovered(line); } } public void assertCatchBlockEndNoException(final Line line) { if (isJDKCompiler) { assertFullyCovered(line); } else { assertEmpty(line); } } public void assertCatchImplicitException(final Line line) { if (isJDKCompiler) { assertFullyCovered(line); } else { assertPartlyCovered(line); } } public void assertCatchBlockEndImplicitException(final Line line) { if (isJDKCompiler) { assertNotCovered(line); } else { assertEmpty(line); } } public void assertFinally(final Line line) { if (isJDKCompiler) { assertEmpty(line); } else { assertFullyCovered(line); } } public void assertFinallyImplicitException(final Line line) { if (isJDKCompiler) { assertEmpty(line); } else { assertNotCovered(line); } } public void assertBlockEndImplicitException(final Line line) { if (isJDKCompiler) { assertEmpty(line); } else { assertFullyCovered(line); } } } ExplicitInitialFrameTest.java000066400000000000000000000016551451257705100375210ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.ExplicitInitialFrameTarget; /** * Test for a methods having a explicit initial frame. */ public class ExplicitInitialFrameTest extends ValidationTestBase { public ExplicitInitialFrameTest() { super(ExplicitInitialFrameTarget.class); } } FieldInitializationInTwoConstructorsTest.java000066400000000000000000000017551451257705100430210ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.FieldInitializationInTwoConstructorsTarget; /** * Test of field initialization in two constructors. */ public class FieldInitializationInTwoConstructorsTest extends ValidationTestBase { public FieldInitializationInTwoConstructorsTest() { super(FieldInitializationInTwoConstructorsTarget.class); } } FinallyTest.java000066400000000000000000000134721451257705100350510ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNull; import java.io.IOException; import java.util.HashMap; import java.util.HashSet; import java.util.Map; import java.util.Set; import org.jacoco.core.internal.instr.InstrSupport; import org.jacoco.core.test.TargetLoader; import org.jacoco.core.test.validation.JavaVersion; import org.jacoco.core.test.validation.Source.Line; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.FinallyTarget; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.ClassNode; import org.objectweb.asm.tree.LineNumberNode; import org.objectweb.asm.tree.MethodNode; /** * Test of filtering of duplicated bytecode that is generated for finally block. */ public class FinallyTest extends ValidationTestBase { private Map tags; public FinallyTest() { super(FinallyTarget.class); } @Before @Override public void setup() throws Exception { super.setup(); tags = new HashMap(); } public void assertFinally(final Line line) { if (isJDKCompiler) { assertEmpty(line); } else { assertFullyCovered(line); } } public void assertTwoRegions1(final Line line) { if (isJDKCompiler && JavaVersion.current().isBefore("1.8")) { // https://bugs.openjdk.java.net/browse/JDK-7008643 assertPartlyCovered(line); } else { assertFullyCovered(line); } } public void assertTwoRegionsReturn1(final Line line) { if (isJDKCompiler && JavaVersion.current().isBefore("1.8")) { // https://bugs.openjdk.java.net/browse/JDK-7008643 assertEmpty(line); } else { assertFullyCovered(line); } } public void assertTwoRegionsReturn2(final Line line) { if (isJDKCompiler && JavaVersion.current().isBefore("1.8")) { // https://bugs.openjdk.java.net/browse/JDK-7008643 assertEmpty(line); } else { assertNotCovered(line); } } public void assertEmptyTry1(final Line line) { if (isJDKCompiler && JavaVersion.current().isBefore("1.8")) { // compiler bug fixed in javac >= 1.8: assertPartlyCovered(line); } else { assertFullyCovered(line); } } public void assertEmptyTry2(final Line line) { if (isJDKCompiler && JavaVersion.current().isBefore("1.8")) { // compiler bug fixed in javac >= 1.8: assertFullyCovered(line); } else { assertEmpty(line); } } public void assertAlwaysCompletesAbruptly0(final Line line) { if (isJDKCompiler) { // uncovered case: assertEmpty(line); } else { assertPartlyCovered(line); } } public void assertAlwaysCompletesAbruptly1(final Line line) { if (isJDKCompiler) { // uncovered case: assertPartlyCovered(line); } else { assertFullyCovered(line); } } @Test @Override public void execute_assertions_in_comments() throws IOException { super.execute_assertions_in_comments(); gotos(); } /** * This test studies placement of GOTO instructions. */ private void gotos() throws IOException { final Set expected = new HashSet(); if (isJDKCompiler) { expected.add("example.2"); } else { expected.add("example.0"); } expected.add("breakStatement.for"); if (isJDKCompiler) { if (JavaVersion.current().isBefore("10")) { // https://bugs.openjdk.java.net/browse/JDK-8180141 expected.add("breakStatement.1"); } else { expected.add("breakStatement"); } expected.add("breakStatement.2"); } else { expected.add("breakStatement"); } if (isJDKCompiler) { expected.add("emptyCatch.2"); } else { expected.add("emptyCatch"); expected.add("emptyCatch.1"); } if (isJDKCompiler) { expected.add("catchNotExecuted.2"); } else { expected.add("catchNotExecuted"); expected.add("catchNotExecuted.1"); } if (isJDKCompiler) { expected.add("nested.5"); expected.add("nested.6"); } else { expected.add("nested.0"); expected.add("nested.3"); } if (isJDKCompiler && JavaVersion.current().isBefore("1.8")) { expected.add("emptyTry.2"); } if (!isJDKCompiler) { expected.add("alwaysCompletesAbruptly.0"); } assertEquals(expected, getTagsWithGotos()); } private Set getTagsWithGotos() throws IOException { final Set gotoTags = new HashSet(); byte[] b = TargetLoader.getClassDataAsBytes(FinallyTarget.class); final ClassNode classNode = new ClassNode(); InstrSupport.classReaderFor(b).accept(classNode, 0); for (final MethodNode m : classNode.methods) { if ("main".equals(m.name)) { // skip it continue; } int lineNumber = -1; for (AbstractInsnNode i : m.instructions) { if (AbstractInsnNode.LINE == i.getType()) { lineNumber = ((LineNumberNode) i).line; } if (Opcodes.GOTO == i.getOpcode()) { String tag = tags.get(Integer.valueOf(lineNumber)); if (tag == null) { throw new AssertionError( "No tag at line " + lineNumber); } gotoTags.add(tag); } } } return gotoTags; } public void tag(final Line line, String tag) { assertFalse("duplicate tag " + tag, tags.containsValue(tag)); assertNull("duplicate tag in " + line, tags.put(Integer.valueOf(line.getNr()), tag)); } } FramesTest.java000066400000000000000000000131461451257705100346660ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import static org.junit.Assert.assertEquals; import java.io.IOException; import java.io.PrintWriter; import java.io.StringWriter; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.internal.instr.InstrSupport; import org.jacoco.core.runtime.IRuntime; import org.jacoco.core.runtime.SystemPropertiesRuntime; import org.jacoco.core.test.TargetLoader; import org.jacoco.core.test.validation.java5.targets.BooleanExpressionsTarget; import org.jacoco.core.test.validation.java5.targets.ClassInitializerTarget; import org.jacoco.core.test.validation.java5.targets.ConstructorsTarget; import org.jacoco.core.test.validation.java5.targets.ControlStructureBeforeSuperConstructorTarget; import org.jacoco.core.test.validation.java5.targets.ControlStructuresTarget; import org.jacoco.core.test.validation.java5.targets.ExceptionsTarget; import org.jacoco.core.test.validation.java5.targets.ExplicitInitialFrameTarget; import org.jacoco.core.test.validation.java5.targets.FieldInitializationInTwoConstructorsTarget; import org.jacoco.core.test.validation.java5.targets.ImplicitFieldInitializationTarget; import org.jacoco.core.test.validation.java5.targets.InterfaceClassInitializerTarget; import org.jacoco.core.test.validation.java5.targets.StructuredLockingTarget; import org.junit.Test; import org.objectweb.asm.ClassReader; import org.objectweb.asm.ClassVisitor; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; import org.objectweb.asm.util.TraceClassVisitor; /** * Tests whether stackmap frames are correctly adjusted. */ public class FramesTest { /** * Stack sizes calculated for instrumented classes might be sometimes bigger * than actually needed. This is an acceptable tradeoff in favor of keeping * track of the actual stack sizes. For test assertions we need to replace * max stack sizes with constant value. */ private static class MaxStackEliminator extends ClassVisitor { public MaxStackEliminator(ClassVisitor cv) { super(InstrSupport.ASM_API_VERSION, cv); } @Override public MethodVisitor visitMethod(int access, String name, String desc, String signature, String[] exceptions) { final MethodVisitor mv = super.visitMethod(access, name, desc, signature, exceptions); return new MethodVisitor(InstrSupport.ASM_API_VERSION, mv) { @Override public void visitMaxs(int maxStack, int maxLocals) { super.visitMaxs(-1, maxLocals); } }; } } private void testFrames(Class target) throws IOException { testFrames(TargetLoader.getClassDataAsBytes(target)); } private void testFrames(byte[] source) throws IOException { IRuntime runtime = new SystemPropertiesRuntime(); Instrumenter instrumenter = new Instrumenter(runtime); source = calculateFrames(source); byte[] actual = instrumenter.instrument(source, "TestTarget"); byte[] expected = calculateFrames(actual); assertEquals(dump(expected), dump(actual)); } private byte[] calculateFrames(byte[] source) { ClassReader rc = InstrSupport.classReaderFor(source); ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_FRAMES); // Adjust Version to 1.6 to enable frames: rc.accept(new ClassVisitor(InstrSupport.ASM_API_VERSION, cw) { @Override public void visit(int version, int access, String name, String signature, String superName, String[] interfaces) { super.visit(Opcodes.V1_6, access, name, signature, superName, interfaces); } }, 0); return cw.toByteArray(); } private String dump(byte[] bytes) { final StringWriter buffer = new StringWriter(); final PrintWriter writer = new PrintWriter(buffer); new ClassReader(bytes).accept( new MaxStackEliminator(new TraceClassVisitor(writer)), ClassReader.EXPAND_FRAMES); return buffer.toString(); } @Test public void boolean_expressions() throws IOException { testFrames(BooleanExpressionsTarget.class); } @Test public void class_initializer() throws IOException { testFrames(ClassInitializerTarget.class); } @Test public void constructors() throws IOException { testFrames(ConstructorsTarget.class); } @Test public void control_structures() throws IOException { testFrames(ControlStructuresTarget.class); } @Test public void control_structure_before_super_constructor() throws IOException { testFrames(ControlStructureBeforeSuperConstructorTarget.class); } @Test public void exceptions() throws IOException { testFrames(ExceptionsTarget.class); } @Test public void explicit_initial_frame() throws IOException { testFrames(ExplicitInitialFrameTarget.class); } @Test public void field_initialization_in_two_constructors() throws IOException { testFrames(FieldInitializationInTwoConstructorsTarget.class); } @Test public void implicit_field_initialization() throws IOException { testFrames(ImplicitFieldInitializationTarget.class); } @Test public void interface_class_initializer() throws IOException { testFrames(InterfaceClassInitializerTarget.class); } @Test public void structured_locking() throws IOException { testFrames(StructuredLockingTarget.class); } } ImplicitFieldInitializationTest.java000066400000000000000000000016761451257705100411040ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.ImplicitFieldInitializationTarget; /** * Test of a implicit field initialization. */ public class ImplicitFieldInitializationTest extends ValidationTestBase { public ImplicitFieldInitializationTest() { super(ImplicitFieldInitializationTarget.class); } } InterfaceClassInitializerTest.java000066400000000000000000000021261451257705100405370ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.InterfaceClassInitializerTarget; /** * Tests of static initializer in interfaces. */ public class InterfaceClassInitializerTest extends ValidationTestBase { public InterfaceClassInitializerTest() { super(InterfaceClassInitializerTarget.class); } @Override protected void run(final Class targetClass) throws Exception { // Force class initialization targetClass.getField("CONST1").get(null); } } StructuredLockingTest.java000066400000000000000000000141031451257705100371160ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; import java.util.Collections; import java.util.HashSet; import java.util.List; import java.util.Set; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.internal.instr.InstrSupport; import org.jacoco.core.runtime.IRuntime; import org.jacoco.core.runtime.SystemPropertiesRuntime; import org.jacoco.core.test.TargetLoader; import org.jacoco.core.test.validation.java5.targets.StructuredLockingTarget; import org.junit.Test; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.ClassNode; import org.objectweb.asm.tree.MethodNode; import org.objectweb.asm.tree.TryCatchBlockNode; import org.objectweb.asm.tree.VarInsnNode; import org.objectweb.asm.tree.analysis.Analyzer; import org.objectweb.asm.tree.analysis.AnalyzerException; import org.objectweb.asm.tree.analysis.BasicInterpreter; import org.objectweb.asm.tree.analysis.BasicValue; import org.objectweb.asm.tree.analysis.Frame; import org.objectweb.asm.tree.analysis.Interpreter; /** * Tests that the invariants specified in chapter * 2.11.10 of the JVM Spec do also hold for instrumented classes. * * This is important because JIT compiler in HotSpot JVM ignores methods with * unstructured locking, so that they executed by interpreter. Android Runtime * also doesn't optimize such methods. * * TODO verification implemented here is incomplete - in particular it is unable * to catch problem described in https://github.com/jacoco/jacoco/issues/626 */ public class StructuredLockingTest { @Test public void testMonitorExit() throws Exception { assertStructuredLocking(TargetLoader .getClassDataAsBytes(StructuredLockingTarget.class)); } private void assertStructuredLocking(byte[] source) throws Exception { IRuntime runtime = new SystemPropertiesRuntime(); Instrumenter instrumenter = new Instrumenter(runtime); byte[] instrumented = instrumenter.instrument(source, "TestTarget"); ClassNode cn = new ClassNode(); InstrSupport.classReaderFor(instrumented).accept(cn, 0); for (MethodNode mn : cn.methods) { assertStructuredLocking(cn.name, mn); } } private void assertStructuredLocking(String owner, MethodNode mn) throws Exception { Analyzer analyzer = new Analyzer( new BasicInterpreter()) { @Override protected Frame newFrame(int nLocals, int nStack) { return new LockFrame(nLocals, nStack); } @Override protected Frame newFrame( Frame src) { return new LockFrame(src); } }; Frame[] frames = analyzer.analyze(owner, mn); // Make sure no locks are left when method exits: for (int i = 0; i < frames.length; i++) { AbstractInsnNode insn = mn.instructions.get(i); switch (insn.getOpcode()) { case Opcodes.IRETURN: case Opcodes.LRETURN: case Opcodes.FRETURN: case Opcodes.DRETURN: case Opcodes.ARETURN: case Opcodes.RETURN: ((LockFrame) frames[i]).assertNoLock("Exit with lock"); break; case Opcodes.ATHROW: List handlers = analyzer.getHandlers(i); if (handlers == null || handlers.isEmpty()) { ((LockFrame) frames[i]).assertNoLock("Exit with lock"); } break; } } // Only instructions protected by a catch-all handler can hold locks: for (int i = 0; i < frames.length; i++) { AbstractInsnNode insn = mn.instructions.get(i); if (insn.getOpcode() > 0) { boolean catchAll = false; List handlers = analyzer.getHandlers(i); if (handlers != null) { for (TryCatchBlockNode node : handlers) { catchAll |= node.type == null; } } if (!catchAll) { ((LockFrame) frames[i]) .assertNoLock("No handlers for insn with lock"); } } } } /** * A Frame implementation that keeps track of the locking state. It is * assumed that the monitor objects are stored in local variables. */ private static class LockFrame extends Frame { Set locks; public LockFrame(final int nLocals, final int nStack) { super(nLocals, nStack); locks = new HashSet(); } public LockFrame(Frame src) { super(src); } @Override public Frame init(Frame src) { locks = new HashSet(((LockFrame) src).locks); return super.init(src); } @Override public void execute(AbstractInsnNode insn, Interpreter interpreter) throws AnalyzerException { super.execute(insn, interpreter); switch (insn.getOpcode()) { case Opcodes.MONITORENTER: // Lock is stored in a local variable: enter(((VarInsnNode) insn.getPrevious()).var); break; case Opcodes.MONITOREXIT: // Lock is stored in a local variable: exit(((VarInsnNode) insn.getPrevious()).var); break; } } void enter(int lock) { assertTrue("multiple ENTER for lock " + lock, locks.add(Integer.valueOf(lock))); } void exit(int lock) { assertTrue("invalid EXIT for lock " + lock, locks.remove(Integer.valueOf(lock))); } @Override public boolean merge(Frame frame, Interpreter interpreter) throws AnalyzerException { this.locks.addAll(((LockFrame) frame).locks); return super.merge(frame, interpreter); } void assertNoLock(String message) { assertEquals(message, Collections.emptySet(), locks); } } } SynchronizedTest.java000066400000000000000000000030241451257705100361220ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.Source.Line; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.SynchronizedTarget; /** * Test of filtering of a bytecode that is generated for a synchronized * statement. */ public class SynchronizedTest extends ValidationTestBase { public SynchronizedTest() { super(SynchronizedTarget.class); } public void assertMonitorEnterImplicitException(final Line line) { if (isJDKCompiler) { assertFullyCovered(line); } else { assertPartlyCovered(line); } } public void assertMonitorExit(final Line line) { if (isJDKCompiler) { // without filter next line covered partly: assertFullyCovered(line); } else { assertEmpty(line); } } public void assertMonitorExitImplicitException(final Line line) { if (isJDKCompiler) { // without filter next line covered partly: assertNotCovered(line); } else { assertEmpty(line); } } } SyntheticTest.java000066400000000000000000000017221451257705100354200ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java5.targets.SyntheticTarget; import org.junit.Test; /** * Test of filtering of synthetic methods. */ public class SyntheticTest extends ValidationTestBase { public SyntheticTest() { super(SyntheticTarget.class); } @Test public void test_method_count() { assertMethodCount(5); } } targets/000077500000000000000000000000001451257705100334125ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5AnnotationGeneratedTarget.java000066400000000000000000000041511451257705100413560ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.nop; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; public class AnnotationGeneratedTarget { private static class RetentionPolicyRuntime { @Retention(RetentionPolicy.RUNTIME) @interface Generated { } @RetentionPolicyRuntime.Generated static void annotatedMethod() { nop(); // assertEmpty() } @RetentionPolicyRuntime.Generated static class AnnotatedClass { AnnotatedClass() { nop(); // assertEmpty() } } } private static class RetentionPolicyClass { @Retention(RetentionPolicy.CLASS) @interface Generated { } @RetentionPolicyClass.Generated static void annotatedMethod() { nop(); // assertEmpty() } @RetentionPolicyClass.Generated static class AnnotatedClass { AnnotatedClass() { nop(); // assertEmpty() } } } private static class RetentionPolicySource { @Retention(RetentionPolicy.SOURCE) @interface Generated { } @RetentionPolicySource.Generated static void annotatedMethod() { nop(); // assertFullyCovered() } @RetentionPolicySource.Generated static class AnnotatedClass { AnnotatedClass() { nop(); // assertFullyCovered() } } } public static void main(String[] args) { RetentionPolicyRuntime.annotatedMethod(); new RetentionPolicyRuntime.AnnotatedClass(); RetentionPolicyClass.annotatedMethod(); new RetentionPolicyClass.AnnotatedClass(); RetentionPolicySource.annotatedMethod(); new RetentionPolicySource.AnnotatedClass(); } } AnnotationInitializerTarget.java000066400000000000000000000014451451257705100417460ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; /** * This test target is an annotation with an initializer. */ public @interface AnnotationInitializerTarget { Object CONST = new Object(); // assertFullyCovered() int value() default 0; // assertEmpty() } AssertTarget.java000066400000000000000000000015701451257705100366700ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.t; /** * This target exercises assert statement. */ public class AssertTarget { // assertFullyCovered() private AssertTarget() { } public static void main(String[] args) { assert t() : "msg"; // assertPartlyCovered(1, 1) } } BadCycleClassTarget.java000066400000000000000000000021641451257705100400630ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import org.jacoco.core.test.validation.targets.Stubs; public class BadCycleClassTarget { public static class Base { static final Child b = new Child(); static { b.someMethod(); } } public static class Child extends Base { static { Stubs.logEvent("childclinit"); // assertFullyCovered() } public Child() { Stubs.logEvent("childinit"); // assertFullyCovered() } void someMethod() { Stubs.logEvent("childsomeMethod"); // assertFullyCovered() } } public static void main(String[] args) { new Child(); } } BooleanExpressionsTarget.java000066400000000000000000000063711451257705100412550ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.f; import static org.jacoco.core.test.validation.targets.Stubs.i1; import static org.jacoco.core.test.validation.targets.Stubs.i2; import static org.jacoco.core.test.validation.targets.Stubs.nop; import static org.jacoco.core.test.validation.targets.Stubs.t; /** * This target exercises boolean expressions. */ public class BooleanExpressionsTarget { public static void main(String[] args) { /* 1. Boolean comparison result (one case) */ nop(i2() > 3); // assertPartlyCovered(1, 1) /* 2. Boolean comparison result (both cases) */ for (int i = 0; i < 2; i++) { nop(i < 1); // assertFullyCovered(0, 2) } /* 3. And */ if (f() & f()) { // assertFullyCovered(1, 1) nop(); } if (f() & t()) { // assertFullyCovered(1, 1) nop(); } if (t() & f()) { // assertFullyCovered(1, 1) nop(); } if (t() & t()) { // assertFullyCovered(1, 1) nop(); } nop(f() & f()); // assertFullyCovered() /* 4. Conditional And */ if (f() && f()) { // assertPartlyCovered(3, 1) nop(); } if (f() && t()) { // assertPartlyCovered(3, 1) nop(); } if (t() && f()) { // assertFullyCovered(2, 2) nop(); } if (t() && t()) { // assertFullyCovered(2, 2) nop(); } nop(f() && f()); // assertPartlyCovered(3, 1) nop(t() && f()); // assertPartlyCovered(2, 2) /* 5. Or */ if (f() | f()) { // assertFullyCovered(1, 1) nop(); } if (f() | t()) { // assertFullyCovered(1, 1) nop(); } if (t() | f()) { // assertFullyCovered(1, 1) nop(); } if (t() | t()) { // assertFullyCovered(1, 1) nop(); } nop(f() | f()); // assertFullyCovered() /* 6. Conditional Or */ if (f() || f()) { // assertFullyCovered(2, 2) nop(); } if (f() || t()) { // assertFullyCovered(2, 2) nop(); } if (t() || f()) { // assertPartlyCovered(3, 1) nop(); } if (t() || t()) { // assertPartlyCovered(3, 1) nop(); } nop(t() || f()); // assertPartlyCovered(3, 1) nop(f() || f()); // assertPartlyCovered(2, 2) /* 7. Exclusive Or */ if (f() ^ f()) { // assertFullyCovered(1, 1) nop(); } if (f() ^ t()) { // assertFullyCovered(1, 1) nop(); } if (t() ^ f()) { // assertFullyCovered(1, 1) nop(); } if (t() ^ t()) { // assertFullyCovered(1, 1) nop(); } nop(f() ^ f()); // assertFullyCovered() /* 8. Conditional Operator */ nop(t() ? i1() : i2()); // assertPartlyCovered(1, 1) nop(f() ? i1() : i2()); // assertPartlyCovered(1, 1) /* 9. Not (one case) */ nop(!t()); // assertPartlyCovered(1, 1) nop(!f()); // assertPartlyCovered(1, 1) /* 10. Not (both cases) */ for (boolean b : new boolean[] { true, false }) { nop(!b); // assertFullyCovered(0, 2) } } } ClassInitializerTarget.java000066400000000000000000000030451451257705100406770ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.i1; import org.jacoco.core.test.validation.targets.Stubs; /** * This test target is a class with a static initializer. */ public class ClassInitializerTarget { /* No code required to initialize these fields: */ public static final int CONST1 = 3; // assertEmpty() public static final String CONST2 = "Hello"; // assertEmpty() /* These fields are initialized within */ public static final int CONST3 = i1(); // assertFullyCovered() public static final Object CONST4 = new Object(); // assertFullyCovered() public static int field1 = 3; // assertFullyCovered() public static String field2 = "Hello"; // assertFullyCovered() public static int field3 = i1(); // assertFullyCovered() public static Object field4 = new Object(); // assertFullyCovered() static { Stubs.nop(); // assertFullyCovered() } private ClassInitializerTarget() { } public static void main(String[] args) { } } ConstructorsTarget.java000066400000000000000000000046231451257705100401410ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.nop; /** * This test target calls different constructors. */ public class ConstructorsTarget { /* not filtered because not private: */ ConstructorsTarget() { // assertFullyCovered() } /* not filtered because has argument: */ private ConstructorsTarget(Object arg) { // assertFullyCovered() } private static class Super extends ConstructorsTarget { private Super() { /* * not filtered because not empty - prepares arguments for super * constructor: */ super(null); // assertFullyCovered() } } private class Inner { /* * not filtered because contains initialization of a field to hold * reference to an instance of outer class that is passed as an * argument: */ private Inner() { // assertFullyCovered() } } private static class InnerStatic { @SuppressWarnings("unused") private final Object field = this; /* * not filtered because not empty - contains initialization of a field: */ private InnerStatic() { // assertFullyCovered() } } /* * not filtered because default constructor for not private inner classes is * not private: */ public static class PublicDefault { // assertFullyCovered() } static class PackageLocalDefault { // assertFullyCovered() } private static class PrivateDefault { // assertEmpty() } private static class PrivateNonEmptyNoArg { private PrivateNonEmptyNoArg() { nop(); // assertFullyCovered() } } private static class PrivateEmptyNoArg { private PrivateEmptyNoArg() { // assertEmpty() } // assertEmpty() } public static void main(String[] args) { new Super(); new ConstructorsTarget().new Inner(); new InnerStatic(); new PublicDefault(); new PackageLocalDefault(); new PrivateDefault(); new PrivateNonEmptyNoArg(); new PrivateEmptyNoArg(); } } ControlStructureBeforeSuperConstructorTarget.java000066400000000000000000000022611451257705100453760ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.f; import static org.jacoco.core.test.validation.targets.Stubs.t; import org.jacoco.core.test.validation.targets.Stubs.SuperClass; /** * This test target has a constructor containing control structures before the * superclass constructor is called. */ public class ControlStructureBeforeSuperConstructorTarget extends SuperClass { public ControlStructureBeforeSuperConstructorTarget() { super(t() || f()); // assertPartlyCovered(3, 1) } public static void main(String[] args) { new ControlStructureBeforeSuperConstructorTarget(); } } ControlStructuresTarget.java000066400000000000000000000130051451257705100411470ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.f; import static org.jacoco.core.test.validation.targets.Stubs.i2; import static org.jacoco.core.test.validation.targets.Stubs.nop; import static org.jacoco.core.test.validation.targets.Stubs.t; import java.util.Collections; /** * This target exercises a set of common Java control structures. */ public class ControlStructuresTarget { public static void main(String[] args) { unconditionalExecution(); missedIfBlock(); executedIfBlock(); missedWhileBlock(); alwaysExecutedWhileBlock(); executedWhileBlock(); executedDoWhileBlock(); missedForBlock(); executedForBlock(); missedForEachBlock(); executedForEachBlock(); tableSwitchWithHit(); continuedTableSwitchWithHit(); tableSwitchWithoutHit(); lookupSwitchWithHit(); continuedLookupSwitchWithHit(); lookupSwitchWithoutHit(); breakStatement(); continueStatement(); conditionalReturn(); implicitReturn(); explicitReturn(); } private static void unconditionalExecution() { nop(); // assertFullyCovered() } private static void missedIfBlock() { if (f()) { // assertFullyCovered(1, 1) nop(); // assertNotCovered() } else { nop(); // assertFullyCovered() } } private static void executedIfBlock() { if (t()) { // assertFullyCovered(1, 1) nop(); // assertFullyCovered() } else { nop(); // assertNotCovered() } } private static void missedWhileBlock() { while (f()) { // assertFullyCovered(1, 1) nop(); // assertNotCovered() } } private static void alwaysExecutedWhileBlock() { while (t()) { // assertFullyCovered(1, 1) if (t()) { break; } } } private static void executedWhileBlock() { int i = 0; while (i++ < 3) { // assertFullyCovered(0, 2) nop(); // assertFullyCovered() } } private static void executedDoWhileBlock() { do { nop(); // assertFullyCovered() } while (f()); // assertFullyCovered(1, 1) } private static void missedForBlock() { for (nop(); f(); nop()) { // assertPartlyCovered(1, 1) nop(); // assertNotCovered() } } private static void executedForBlock() { for (int j = 0; j < 1; j++) { // assertFullyCovered(0, 2) nop(); // assertFullyCovered() } } private static void missedForEachBlock() { for (Object o : Collections.emptyList()) { // assertPartlyCovered(1, 1) nop(o); // assertNotCovered() } } private static void executedForEachBlock() { for (Object o : Collections.singleton(new Object())) { // assertFullyCovered(0,2) nop(o); // assertFullyCovered() } } private static void tableSwitchWithHit() { switch (i2()) { // assertFullyCovered(3, 1) case 1: nop(); // assertNotCovered() break; case 2: nop(); // assertFullyCovered() break; case 3: nop(); // assertNotCovered() break; default: nop(); // assertNotCovered() break; } } private static void continuedTableSwitchWithHit() { switch (i2()) { // assertFullyCovered(3, 1) case 1: nop(); // assertNotCovered() case 2: nop(); // assertFullyCovered() case 3: nop(); // assertFullyCovered() default: nop(); // assertFullyCovered() } } private static void tableSwitchWithoutHit() { switch (i2()) { // assertFullyCovered(3, 1) case 3: nop(); // assertNotCovered() break; case 4: nop(); // assertNotCovered() break; case 5: nop(); // assertNotCovered() break; default: nop(); // assertFullyCovered() break; } } private static void lookupSwitchWithHit() { switch (i2()) { // assertFullyCovered(3, 1) case -123: nop(); // assertNotCovered() break; case 2: nop(); // assertFullyCovered() break; case 456: nop(); // assertNotCovered() break; default: nop(); // assertNotCovered() break; } } private static void continuedLookupSwitchWithHit() { switch (i2()) { // assertFullyCovered(3, 1) case -123: nop(); // assertNotCovered() case 2: nop(); // assertFullyCovered() case 456: nop(); // assertFullyCovered() default: nop(); // assertFullyCovered() } } private static void lookupSwitchWithoutHit() { switch (i2()) { // assertFullyCovered(3, 1) case -123: nop(); // assertNotCovered() break; case 456: nop(); // assertNotCovered() break; case 789: nop(); // assertNotCovered() break; default: nop(); // assertFullyCovered() break; } } private static void breakStatement() { while (true) { if (t()) { break; // assertFullyCovered() } nop(); // assertNotCovered() } } private static void continueStatement() { for (int j = 0; j < 1; j++) { if (t()) { continue; // assertFullyCovered() } nop(); // assertNotCovered() } } private static void conditionalReturn() { if (t()) { return; // assertFullyCovered() } nop(); // assertNotCovered() } private static void implicitReturn() { } // assertFullyCovered() private static void explicitReturn() { return; // assertFullyCovered() } // assertEmpty() } EnumConstructorTarget.java000066400000000000000000000027671451257705100406120ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.nop; /** * This test target is an enum constructor. */ public class EnumConstructorTarget { /* * Implicit constructor should be filtered. without filter next line is * partly covered: */ private enum ImplicitConstructor { // assertFullyCovered() } /* Explicit non empty constructor should not be filtered: */ private enum ExplicitNonEmptyConstructor { ; ExplicitNonEmptyConstructor() { nop(); // assertNotCovered() } } /* Explicit empty constructor should be filtered: */ private enum ExplicitEmptyConstructor { ; ExplicitEmptyConstructor() { /* without filter next line is not covered: */ } // assertEmpty() ExplicitEmptyConstructor(Object p) { } // assertNotCovered() } public static void main(String[] args) { ImplicitConstructor.values(); ExplicitEmptyConstructor.values(); ExplicitNonEmptyConstructor.values(); } } EnumImplicitMethodsTarget.java000066400000000000000000000032701451257705100413510ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import org.jacoco.core.test.validation.targets.Stubs; public enum EnumImplicitMethodsTarget { // assertFullyCovered() CONST(Stubs.f() ? new Object() : new Object()); // assertPartlyCovered(1, 1) static { } // assertFullyCovered() /** * Unlike in {@link ConstructorsTarget regular classes}, even if enum has * explicit constructor, {@code clinit} method in any case has a reference * to the line of enum definition. */ EnumImplicitMethodsTarget(Object o) { // assertFullyCovered() } // assertFullyCovered() /** * This method should not be excluded from analysis unlike implicitly * created {@link #valueOf(String)} method that refers to the line of enum * definition in case of javac and to the first line in case of ECJ. */ public void valueOf() { } // assertNotCovered() /** * This method should not be excluded from analysis unlike implicitly * created {@link #values()} method that refers to the line of enum * definition in case of javac and to the first line in case of ECJ. */ public void values(Object o) { } // assertNotCovered() public static void main(String[] args) { } } EnumSwitchTarget.java000066400000000000000000000020001451257705100375020ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.nop; /** * This test target is a switch statement with a enum. */ public class EnumSwitchTarget { private enum E { V1, V2 } private static void example(E e) { switch (e) { // assertSwitch() case V1: nop("V1"); break; case V2: default: nop("V2"); break; } } public static void main(String[] args) { example(E.V1); example(E.V2); } } ExceptionsTarget.java000066400000000000000000000104351451257705100375500ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.ex; import static org.jacoco.core.test.validation.targets.Stubs.f; import static org.jacoco.core.test.validation.targets.Stubs.nop; import org.jacoco.core.test.validation.targets.Stubs.StubException; /** * This target produces exception based control flow examples. */ public class ExceptionsTarget { public static void main(String[] args) { try { implicitNullPointerException(null); } catch (NullPointerException e) { } try { implicitException(); } catch (StubException e) { } try { explicitException(); } catch (StubException e) { } noExceptionTryCatch(); implicitExceptionTryCatch(); implicitExceptionTryCatchAfterCondition(); explicitExceptionTryCatch(); noExceptionFinally(); try { explicitExceptionFinally(); } catch (StubException e) { } try { implicitExceptionFinally(); } catch (StubException e) { } } /** * Currently no coverage at all, as we don't see when a block aborts * somewhere in the middle. */ private static void implicitNullPointerException(int[] a) { nop(); // assertNotCovered() a[0] = 0; // assertNotCovered() nop(); // assertNotCovered() } /** * For each line with method invocations a extra probe is inserted. * Therefore the lines before the exception are marked as covered. */ private static void implicitException() { nop(); // assertFullyCovered() ex(); // assertNotCovered() nop(); // assertNotCovered() } private static void explicitException() { nop(); // assertFullyCovered() throw new StubException(); // assertFullyCovered() } private static void noExceptionTryCatch() { nop(); // assertFullyCovered() try { nop(); // assertFullyCovered() } catch (StubException e) { // assertCatchNoException() nop(); // assertNotCovered() } // assertCatchBlockEndNoException() } // assertFullyCovered() private static void implicitExceptionTryCatch() { nop(); // assertFullyCovered() try { nop(); // assertFullyCovered() ex(); // assertNotCovered() nop(); // assertNotCovered() } catch (StubException e) { // assertCatchImplicitException() nop(); // assertFullyCovered() } // assertCatchBlockEndImplicitException() } // assertFullyCovered() /** * As the try/catch block is entered at one branch of the condition should * be marked as executed */ private static void implicitExceptionTryCatchAfterCondition() { if (f()) { // assertFullyCovered(1, 1) return; } try { ex(); // assertNotCovered() } catch (StubException e) { nop(); // assertFullyCovered() } } private static void explicitExceptionTryCatch() { nop(); // assertFullyCovered() try { nop(); // assertFullyCovered() throw new StubException(); // assertFullyCovered() } catch (StubException e) { // assertFullyCovered() nop(); // assertFullyCovered() } // assertEmpty() } // assertFullyCovered() private static void noExceptionFinally() { nop(); // assertFullyCovered() try { nop(); // assertFullyCovered() } finally { // assertFinally() nop(); // assertFullyCovered() } // assertEmpty() } // assertFullyCovered() private static void implicitExceptionFinally() { nop(); // assertFullyCovered() try { nop(); // assertFullyCovered() ex(); // assertNotCovered() nop(); // assertNotCovered() } finally { // assertFinallyImplicitException() nop(); // assertFullyCovered() } // assertEmpty() } // assertNotCovered() private static void explicitExceptionFinally() { nop(); // assertFullyCovered() try { nop(); // assertFullyCovered() throw new StubException(); // assertFullyCovered() } finally { // assertFinally() nop(); // assertFullyCovered() } // assertBlockEndImplicitException() } // assertEmpty() } ExplicitInitialFrameTarget.java000066400000000000000000000017311451257705100414740ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.f; import static org.jacoco.core.test.validation.targets.Stubs.nop; /** * This test target needs an explicit initial frame as the first instruction * already is a jump target. */ public class ExplicitInitialFrameTarget { public static void main(String[] args) { do { nop(); // assertFullyCovered() } while (f()); } } FieldInitializationInTwoConstructorsTarget.java000066400000000000000000000021271451257705100447730ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; /** * This test target has instance members with initialization in two * constructors. */ public class FieldInitializationInTwoConstructorsTarget { Object field1 = null; // assertPartlyCovered() int field2 = 123; // assertPartlyCovered() public FieldInitializationInTwoConstructorsTarget() { } // assertFullyCovered() public FieldInitializationInTwoConstructorsTarget(String arg) { } // assertNotCovered() public static void main(String[] args) { new FieldInitializationInTwoConstructorsTarget(); } } FinallyTarget.java000066400000000000000000000103301451257705100370170ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.ex; import static org.jacoco.core.test.validation.targets.Stubs.f; import static org.jacoco.core.test.validation.targets.Stubs.nop; import static org.jacoco.core.test.validation.targets.Stubs.t; public class FinallyTarget { /** *
	 *   InputStream in = null;
	 *   try {
	 *     in = ...;
	 *     ...
	 *   } finally {
	 *     if (in != null) {
	 *       in.close();
	 *     }
	 *   }
	 * 
*/ private static void example(boolean t) { Object in = null; try { in = open(t); } finally { // assertFinally() tag("example.0") if (in != null) { // assertFullyCovered(0, 2) nop(); // assertFullyCovered() tag("example.2") } // assertEmpty() } // assertEmpty() } private static Object open(boolean t) { ex(t); return new Object(); } /** * GOTO instructions at the end of duplicates of finally block might have * line number of a last instruction of finally block and hence lead to * unexpected coverage results, like for example in case of ECJ for * {@link FinallyTarget#catchNotExecuted()}, * {@link FinallyTarget#emptyCatch()}. So we decided to ignore them, even if * they can correspond to a real break statement. *

* See also JDK-8180141 and * JDK-7008643. */ private static void breakStatement() { for (int i = 0; i < 1; i++) { // tag("breakStatement.for") try { if (f()) { break; // assertEmpty() tag("breakStatement") } } finally { nop("finally"); // assertFullyCovered() tag("breakStatement.1") } // assertEmpty() tag("breakStatement.2") } } private static void catchNotExecuted() { try { nop("try"); } catch (Exception e) { // tag("catchNotExecuted") nop("catch"); // assertNotCovered() } finally { // assertEmpty() nop("finally"); // assertFullyCovered() tag("catchNotExecuted.1") } // assertEmpty() tag("catchNotExecuted.2") } private static void emptyCatch() { try { nop("try"); } catch (Exception e) { // tag("emptyCatch") /* empty */ } finally { // assertEmpty() nop("finally"); // assertFullyCovered() tag("emptyCatch.1") } // assertEmpty() tag("emptyCatch.2") } private static void twoRegions() { try { /* jump to another region associated with same handler: */ if (t()) { // assertFullyCovered(1, 1) nop(); // assertFullyCovered() return; // assertTwoRegionsReturn1() } else { nop(); // assertNotCovered() return; // assertTwoRegionsReturn2() } } finally { // assertEmpty() nop(); // assertTwoRegions1() } // assertEmpty() } private static void nested() { try { nop(); } finally { // assertFinally() tag("nested.0") try { // assertEmpty() nop(); // assertFullyCovered() } finally { // assertFinally() tag("nested.3") nop(); // assertFullyCovered() } // assertEmpty() tag("nested.5") } // assertEmpty() tag("nested.6") } private static void emptyTry() { try { /* empty */ } finally { // assertEmpty() nop(); // assertEmptyTry1() } // assertEmptyTry2() tag("emptyTry.2") } @SuppressWarnings("finally") private static void alwaysCompletesAbruptly() { try { nop(); } finally { // assertAlwaysCompletesAbruptly0()tag("alwaysCompletesAbruptly.0") return; // assertAlwaysCompletesAbruptly1() } // assertEmpty() } public static void main(String[] args) { example(false); try { example(true); } catch (Exception ignore) { } breakStatement(); catchNotExecuted(); emptyCatch(); twoRegions(); nested(); emptyTry(); alwaysCompletesAbruptly(); } } ImplicitFieldInitializationTarget.java000066400000000000000000000017371451257705100430620ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; /** * This test target has instance members with implicit initializers. */ public class ImplicitFieldInitializationTarget { // assertFullyCovered() Object field1; // assertEmpty() Object field2 = this; // assertFullyCovered() int field3; // assertEmpty() int field4 = 2000; // assertFullyCovered() public static void main(String[] args) { new ImplicitFieldInitializationTarget(); } } InterfaceClassInitializerTarget.java000066400000000000000000000021421451257705100425150ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.i1; /** * This test target is an interface with a class initializer. */ public interface InterfaceClassInitializerTarget { /* No code required to initialize these fields: */ static final int CONST1 = 12345; // assertEmpty() static final String CONST2 = "const"; // assertEmpty() /* These fields are initialized within */ static final int CONST3 = i1(); // assertFullyCovered() static final Object CONST4 = new Object(); // assertFullyCovered() } StructuredLockingTarget.java000066400000000000000000000021611451257705100410770ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.nop; /** * This target uses synchronized blocks which compile to try/catch statements. */ public class StructuredLockingTarget { static void simple() { Object lock1 = new Object(); synchronized (lock1) { nop(); } } static void nested() { Object lock1 = new Object(); synchronized (lock1) { nop(); Object lock2 = new Object(); synchronized (lock2) { nop(); } nop(); } } public static void main(String[] args) { simple(); nested(); } } SynchronizedTarget.java000066400000000000000000000033471451257705100401120ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; import static org.jacoco.core.test.validation.targets.Stubs.ex; import static org.jacoco.core.test.validation.targets.Stubs.nop; import org.jacoco.core.test.validation.targets.Stubs.StubException; /** * This test target is a synchronized statement. */ public class SynchronizedTarget { private static final Object lock = new Object(); private static void normal() { nop(); // assertFullyCovered() /* when compiled with ECJ next line covered partly without filter: */ synchronized (lock) { // assertFullyCovered() nop(); // assertFullyCovered() } // assertMonitorExit() nop(); // assertFullyCovered() } private static void explicitException() { synchronized (lock) { // assertFullyCovered() throw new StubException(); // assertFullyCovered() } // assertEmpty() } private static void implicitException() { synchronized (lock) { // assertMonitorEnterImplicitException() ex(); // assertNotCovered() } // assertMonitorExitImplicitException() } public static void main(String[] args) { normal(); try { explicitException(); } catch (StubException e) { } try { implicitException(); } catch (StubException e) { } } } SyntheticTarget.java000066400000000000000000000035271451257705100374050ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java5/src/org/jacoco/core/test/validation/java5/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java5.targets; /** * This test target results in synthetic methods. */ public class SyntheticTarget { // assertEmpty() private static int counter; // assertEmpty() /** * {@link org.jacoco.core.test.validation.java5.targets.ConstructorsTarget * Default constructor will refer to a line of class definition}, so that we * define constructor explicitly in order to verify that we filter all other * constructions here that might refer to line of class definition. */ private SyntheticTarget() { } static class Inner extends SyntheticTarget { // assertEmpty() Inner() { } /** * Access to private field of outer class causes creation of synthetic * methods in it. In case of javac those methods refer to the line of * outer class definition, in case of ECJ - to the line of field. */ private static void inc() { counter = counter + 2; } /** * Difference of return type with overridden method causes creation of * synthetic bridge method in this class. In case of javac this method * refers to the line of inner class definition, in case of EJC - to the * first line of file. */ @Override public String get() { return null; } } public Object get() { return null; } public static void main(String[] args) { Inner.inc(); } } jacoco-0.8.11/org.jacoco.core.test.validation.java7/000077500000000000000000000000001451257705100221375ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java7/.classpath000066400000000000000000000013711451257705100241240ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.core.test.validation.java7/.project000066400000000000000000000013561451257705100236130ustar00rootroot00000000000000 org.jacoco.core.test.validation.java7 org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.core.test.validation.java7/pom.xml000066400000000000000000000023401451257705100234530ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.core.test.validation 0.8.11 ../org.jacoco.core.test.validation org.jacoco.core.test.validation.java7 JaCoCo :: Test :: Core :: Validation Java 7 7 ${project.groupId} org.jacoco.core.test jacoco-0.8.11/org.jacoco.core.test.validation.java7/src/000077500000000000000000000000001451257705100227265ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java7/src/org/000077500000000000000000000000001451257705100235155ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java7/src/org/jacoco/000077500000000000000000000000001451257705100247535ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java7/src/org/jacoco/core/000077500000000000000000000000001451257705100257035ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java7/src/org/jacoco/core/test/000077500000000000000000000000001451257705100266625ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java7/src/org/jacoco/core/test/validation/000077500000000000000000000000001451257705100310145ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java7/src/org/jacoco/core/test/validation/java7/000077500000000000000000000000001451257705100320245ustar00rootroot00000000000000StringSwitchTest.java000066400000000000000000000016601451257705100361030ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java7/src/org/jacoco/core/test/validation/java7/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java7; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java7.targets.StringSwitchTarget; /** * Test of filtering of a bytecode that is generated for a String in switch * statement. */ public class StringSwitchTest extends ValidationTestBase { public StringSwitchTest() { super(StringSwitchTarget.class); } } TryWithResourcesTest.java000066400000000000000000000046771451257705100367730ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java7/src/org/jacoco/core/test/validation/java7/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java7; import org.jacoco.core.test.validation.JavaVersion; import org.jacoco.core.test.validation.Source.Line; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java7.targets.TryWithResourcesTarget; /** * Test of filtering of a bytecode that is generated for a try-with-resources * statement. */ public class TryWithResourcesTest extends ValidationTestBase { public TryWithResourcesTest() { super(TryWithResourcesTarget.class); } public void assertTry(final Line line) { // without filter this line is covered partly: if (!isJDKCompiler || JavaVersion.current().isBefore("11")) { assertFullyCovered(line); } else { assertEmpty(line); } } public void assertReturnInBodyClose(final Line line) { // without filter next line has branches: if (isJDKCompiler) { // https://bugs.openjdk.java.net/browse/JDK-8134759 // javac 7 and 8 up to 8u92 are affected if (JavaVersion.current().isBefore("1.8.0_92")) { assertFullyCovered(line); } else { assertEmpty(line); } } else { assertEmpty(line); } } public void assertHandwritten(final Line line) { if (isJDKCompiler) { assertEmpty(line); } else { assertFullyCovered(line, 1, 1); } } public void assertEmptyClose(final Line line) { if (!isJDKCompiler) { assertPartlyCovered(line, 7, 1); } else if (JavaVersion.current().isBefore("8")) { assertPartlyCovered(line, 6, 2); } else if (JavaVersion.current().isBefore("9")) { assertPartlyCovered(line, 2, 2); } else { assertFullyCovered(line); } } public void assertThrowInBodyClose(final Line line) { // not filtered if (!isJDKCompiler) { assertNotCovered(line, 6, 0); } else if (JavaVersion.current().isBefore("9")) { assertNotCovered(line, 4, 0); } else if (JavaVersion.current().isBefore("11")) { assertNotCovered(line); } else { assertEmpty(line); } } } targets/000077500000000000000000000000001451257705100334165ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java7/src/org/jacoco/core/test/validation/java7StringSwitchTarget.java000066400000000000000000000051531451257705100400640ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java7/src/org/jacoco/core/test/validation/java7/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java7.targets; import static org.jacoco.core.test.validation.targets.Stubs.nop; /** * This test target is a switch statement with a String. */ public class StringSwitchTarget { private static void covered(Object s) { switch (String.valueOf(s)) { // assertFullyCovered(0, 4) case "a": nop("case a"); // assertFullyCovered() break; case "b": nop("case b"); // assertFullyCovered() break; case "\0a": nop("case \0a"); // assertFullyCovered() break; default: nop("case default"); // assertFullyCovered() break; } } private static void notCovered(Object s) { switch (String.valueOf(s)) { // assertNotCovered(4, 0) case "a": nop("case a"); break; case "b": nop("case b"); break; case "\0a": nop("case \0a"); break; default: nop("default"); break; } } private static void handwritten(String s) { int c = -1; switch (s.hashCode()) { // assertFullyCovered(2, 1) case 97: if ("a".equals(s)) { // assertFullyCovered(1, 1) c = 0; } else if ("\0a".equals(s)) { c = 1; } break; case 98: if ("b".equals(s)) { c = 2; } break; } switch (c) { // assertFullyCovered(3, 1) case 0: nop("case a"); // assertFullyCovered() break; case 1: nop("case \0a"); // assertNotCovered() break; case 2: nop("case b"); break; default: nop("default"); break; } } /** * In this case javac generates LOOKUPSWITCH for second switch. */ private static void lookupswitch(Object s) { switch (String.valueOf(s)) { // assertNotCovered(3, 0) case "a": nop("case a"); break; case "b": nop("case b"); break; default: nop("default"); break; } } private static void default_is_first(Object s) { switch (String.valueOf(s)) { // assertFullyCovered(0, 2) default: nop("default"); break; case "a": nop("case a"); break; } } public static void main(String[] args) { covered(""); covered("a"); covered("b"); covered("\0a"); handwritten("a"); default_is_first(""); default_is_first("a"); } } TryWithResourcesTarget.java000066400000000000000000000120701451257705100407350ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java7/src/org/jacoco/core/test/validation/java7/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java7.targets; import static org.jacoco.core.test.validation.targets.Stubs.f; import static org.jacoco.core.test.validation.targets.Stubs.nop; import java.io.Closeable; import java.io.IOException; /** * This test target is a try-with-resources statement. */ public class TryWithResourcesTarget { private static class Resource implements Closeable { @Override public void close() { } } /** * Closing performed using {@link org.objectweb.asm.Opcodes#INVOKEVIRTUAL} * or {@link org.objectweb.asm.Opcodes#INVOKEINTERFACE} depending on a class * of resource. */ private static Object test() throws Exception { nop(); // assertFullyCovered() try ( // assertTry() Resource r1 = new Resource(); // assertFullyCovered() Closeable r2 = new Resource(); // assertFullyCovered() AutoCloseable r3 = new Resource() // assertFullyCovered() ) { return read(r1, r2, r3); // assertFullyCovered() /* without filter next line has branches: */ } // assertEmpty() catch (Exception e) { nop(); // assertNotCovered() throw e; } finally { nop(); // assertFullyCovered() } } private static void test2() throws Exception { nop(); // assertFullyCovered() try ( // assertTry() Resource r1 = new Resource(); // assertFullyCovered() Closeable r2 = new Resource(); // assertFullyCovered() AutoCloseable r3 = new Resource() // assertFullyCovered() ) { read(r1, r2, r3); // assertFullyCovered() /* without filter next line has branches: */ } // assertEmpty() catch (Exception e) { nop(); // assertNotCovered() } finally { nop(); // assertFullyCovered() } nop(); // assertFullyCovered() } private static Object returnInBody() throws IOException { try ( // assertTry() Closeable r = new Resource() // assertFullyCovered() ) { return read(r); // assertFullyCovered() } // assertReturnInBodyClose() } private static void nested() { try ( // assertTry() Resource r1 = new Resource() // assertFullyCovered() ) { try ( // assertTry() Resource r2 = new Resource() // assertFullyCovered() ) { nop(r1.toString() + r2.toString()); // assertFullyCovered() } // assertEmpty() catch (Exception e) { nop(); // assertNotCovered() } finally { nop(); // assertFullyCovered() } } // assertEmpty() catch (Exception e) { nop(); // assertNotCovered() } finally { try ( // assertTry() Resource r2 = new Resource() // assertFullyCovered() ) { nop(r2); // assertFullyCovered() } // assertEmpty() catch (Exception e) { nop(); // assertNotCovered() } finally { nop(); // assertFullyCovered() } } } /** * In this case bytecode will contain 3 copies of finally * block, each containing 2 branches, resulting in 6 branches in total. One * could think that this is artifact of try-with-resources, but the same * happens without it. */ private static Object returnInCatch() { try ( // assertTry() Resource r = new Resource() // assertFullyCovered() ) { read(r); /* without filter next line has branches: */ } // assertEmpty() catch (Exception e) { return null; } finally { nop(!f()); // assertPartlyCovered(1, 1) } try { // assertEmpty() read(new Resource()); } catch (Exception e) { return null; } finally { nop(!f()); // assertPartlyCovered(1, 1) } return null; } private static Object read(Object r1, Object r2, Object r3) { return r1.toString() + r2.toString() + r3.toString(); } private static Object read(Object r1) { return r1.toString(); } /* * Corner cases */ private static void empty() throws Exception { try ( // assertTry() Closeable r = new Resource() // assertFullyCovered() ) { } // assertEmptyClose() } private static void handwritten() throws IOException { Closeable r = new Resource(); Throwable primaryExc = null; try { nop(r); } catch (Throwable t) { primaryExc = t; throw t; } finally { if (r != null) { // assertHandwritten() if (primaryExc != null) { try { r.close(); } catch (Throwable suppressedExc) { primaryExc.addSuppressed(suppressedExc); } } else { r.close(); } } } } private static void throwInBody() throws IOException { try ( // assertNotCovered() Closeable r = new Resource()) { nop(r); throw new RuntimeException(); } // assertThrowInBodyClose() } public static void main(String[] args) throws Exception { test(); test2(); returnInBody(); nested(); returnInCatch(); empty(); handwritten(); } } jacoco-0.8.11/org.jacoco.core.test.validation.java8/000077500000000000000000000000001451257705100221405ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/.classpath000066400000000000000000000013711451257705100241250ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.core.test.validation.java8/.project000066400000000000000000000013561451257705100236140ustar00rootroot00000000000000 org.jacoco.core.test.validation.java8 org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.core.test.validation.java8/pom.xml000066400000000000000000000023401451257705100234540ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.core.test.validation 0.8.11 ../org.jacoco.core.test.validation org.jacoco.core.test.validation.java8 JaCoCo :: Test :: Core :: Validation Java 8 8 ${project.groupId} org.jacoco.core.test jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/000077500000000000000000000000001451257705100227275ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/000077500000000000000000000000001451257705100235165ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/000077500000000000000000000000001451257705100247545ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/000077500000000000000000000000001451257705100257045ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/000077500000000000000000000000001451257705100266635ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/000077500000000000000000000000001451257705100310155ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/000077500000000000000000000000001451257705100320265ustar00rootroot00000000000000AnnotationOnLocalVariableTest.java000066400000000000000000000017431451257705100405070ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java8; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java8.targets.AnnotationOnLocalVariableTarget; /** * Test of ASM bug * #317815 */ public class AnnotationOnLocalVariableTest extends ValidationTestBase { public AnnotationOnLocalVariableTest() { super(AnnotationOnLocalVariableTarget.class); } } BadCycleInterfaceTest.java000066400000000000000000000044111451257705100367410ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java8; import org.jacoco.core.test.validation.JavaVersion; import org.jacoco.core.test.validation.Source.Line; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java8.targets.BadCycleInterfaceTarget; import org.junit.Test; /** * Test of "bad cycles" with interfaces. */ public class BadCycleInterfaceTest extends ValidationTestBase { public BadCycleInterfaceTest() throws Exception { super(BadCycleInterfaceTarget.class); } @Test public void method_execution_sequence() throws Exception { if (JavaVersion.current().isBefore("1.8.0_152")) { assertLogEvents("baseclinit", "childdefaultmethod", "childclinit", "childstaticmethod"); } else { assertLogEvents("childclinit", "childstaticmethod"); } } public void assertBaseClInit(final Line line) { if (JavaVersion.current().isBefore("1.8.0_152")) { // Incorrect interpetation of JVMS 5.5 in JDK 8 causes a default // method to be called before the static initializer of an interface // (see JDK-8098557 and JDK-8164302): assertFullyCovered(line); } else { // This shouldn't happen with JDK 9 (see also JDK-8043275) // and starting with JDK 8u152 (see JDK-8167607): assertEmpty(line); } } public void assertChildDefault(final Line line) throws Exception { if (JavaVersion.current().isBefore("1.8.0_152")) { // Incorrect interpetation of JVMS 5.5 in JDK 8 causes a default // method to be called before the static initializer of an interface // (see JDK-8098557 and JDK-8164302): assertFullyCovered(line); } else { // This shouldn't happen with JDK 9 (see also JDK-8043275) // and starting with JDK 8u152 (see JDK-8167607): assertNotCovered(line); } } } BootstrapMethodReferenceTest.java000066400000000000000000000100311451257705100404020ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java8; import static org.junit.Assert.assertEquals; import java.lang.invoke.CallSite; import java.lang.invoke.ConstantCallSite; import java.lang.invoke.MethodHandles; import java.lang.invoke.MethodType; import java.lang.reflect.InvocationTargetException; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.runtime.IRuntime; import org.jacoco.core.runtime.RuntimeData; import org.jacoco.core.runtime.SystemPropertiesRuntime; import org.jacoco.core.test.TargetLoader; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.Handle; import org.objectweb.asm.Label; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; /** * Test of ASM bug * #317748 that * caused * {@code java.lang.ClassFormatError: Short length on BootstrapMethods in class file} * during instrumentation. */ public class BootstrapMethodReferenceTest { private IRuntime runtime; private Instrumenter instrumenter; @Before public void setup() throws Exception { runtime = new SystemPropertiesRuntime(); instrumenter = new Instrumenter(runtime); runtime.startup(new RuntimeData()); } @After public void teardown() { runtime.shutdown(); } @Test public void test() throws Exception { final String className = "Example"; final ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_FRAMES); cw.visit(Opcodes.V1_7, Opcodes.ACC_PUBLIC, className, null, "java/lang/Object", null); final MethodVisitor mv = cw.visitMethod( Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC, "run", "()I", null, null); mv.visitCode(); addCauseOfResizeInstructions(mv); final MethodType methodType = MethodType.methodType(CallSite.class, MethodHandles.Lookup.class, String.class, MethodType.class); final Handle handle = new Handle(Opcodes.H_INVOKESTATIC, this.getClass().getCanonicalName().replace('.', '/'), "bootstrap", methodType.toMethodDescriptorString(), false); mv.visitInvokeDynamicInsn("invoke", "()I", handle); mv.visitInsn(Opcodes.IRETURN); mv.visitMaxs(1, 0); mv.visitEnd(); cw.visitEnd(); final byte[] original = cw.toByteArray(); assertEquals(42, run(className, original)); final byte[] instrumented = instrumenter.instrument(original, className); assertEquals(42, run(className, instrumented)); } private static int run(final String className, final byte[] bytes) throws ClassNotFoundException, NoSuchMethodException, InvocationTargetException, IllegalAccessException { final Integer result = (Integer) new TargetLoader() .add(className, bytes).getMethod("run").invoke(null); return result.intValue(); } /** * Adds code that triggers usage of * {@link org.objectweb.asm.MethodWriter#COMPUTE_INSERTED_FRAMES} during * instrumentation. */ private static void addCauseOfResizeInstructions(final MethodVisitor mv) { mv.visitInsn(Opcodes.ICONST_0); mv.visitInsn(Opcodes.ICONST_1); final Label target = new Label(); mv.visitJumpInsn(Opcodes.IFLE, target); for (int i = 0; i < Short.MAX_VALUE; i++) { mv.visitInsn(Opcodes.NOP); } mv.visitLabel(target); } public static CallSite bootstrap(final MethodHandles.Lookup caller, final String name, final MethodType type) throws Exception { return new ConstantCallSite( caller.findStatic(BootstrapMethodReferenceTest.class, "callTarget", MethodType.methodType(int.class))); } public static int callTarget() { return 42; } } InterfaceDefaultMethodsTest.java000066400000000000000000000017041451257705100402050ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java8; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java8.targets.InterfaceDefaultMethodsTarget; /** * Tests of static initializer and default methods in interfaces. */ public class InterfaceDefaultMethodsTest extends ValidationTestBase { public InterfaceDefaultMethodsTest() { super(InterfaceDefaultMethodsTarget.class); } } InterfaceOnlyDefaultMethodsTest.java000066400000000000000000000016751451257705100410560ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java8; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java8.targets.InterfaceOnlyDefaultMethodsTarget; /** * Tests of default methods in interfaces. */ public class InterfaceOnlyDefaultMethodsTest extends ValidationTestBase { public InterfaceOnlyDefaultMethodsTest() { super(InterfaceOnlyDefaultMethodsTarget.class); } } LambdaExpressionsTest.java000066400000000000000000000016251451257705100371010ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java8; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java8.targets.LambdaExpressionsTarget; /** * Tests for different lambda expressions. */ public class LambdaExpressionsTest extends ValidationTestBase { public LambdaExpressionsTest() { super(LambdaExpressionsTarget.class); } } LambdaInInterfaceTest.java000066400000000000000000000020611451257705100367410ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java8; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.java8.targets.LambdaInInterfaceTarget; /** * Tests a constant with a lambda value in an interface. */ public class LambdaInInterfaceTest extends ValidationTestBase { public LambdaInInterfaceTest() { super(LambdaInInterfaceTarget.class); } @Override protected void run(final Class targetClass) throws Exception { ((Runnable) targetClass.getField("RUN").get(null)).run(); } } targets/000077500000000000000000000000001451257705100334205ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8AnnotationOnLocalVariableTarget.java000066400000000000000000000022341451257705100424630ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java8.targets; import java.lang.annotation.Documented; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; /** * This test target contains annotation on local variable. */ public class AnnotationOnLocalVariableTarget { @Documented @Retention(RetentionPolicy.CLASS) @Target(ElementType.TYPE_USE) @interface NonNull { } private static Object legacy() { return new Object(); } public static void main(String[] args) { @NonNull Object o = legacy(); // assertFullyCovered() } } BadCycleInterfaceTarget.java000066400000000000000000000025361451257705100407270ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java8.targets; import org.jacoco.core.test.validation.targets.Stubs; public class BadCycleInterfaceTarget { public interface Base { static final Object BASE_CONST = new Child() { { Stubs.logEvent("baseclinit"); // assertBaseClInit() } }.childDefaultMethod(); default void baseDefaultMethod() { } } public interface Child extends Base { static final Object CHILD_CONST = new Object() { { Stubs.logEvent("childclinit"); // assertFullyCovered() } }; default Object childDefaultMethod() { Stubs.logEvent("childdefaultmethod"); // assertChildDefault() return null; } static void childStaticMethod() { Stubs.logEvent("childstaticmethod"); // assertFullyCovered() } } public static void main(String[] args) { Child.childStaticMethod(); } } InterfaceDefaultMethodsTarget.java000066400000000000000000000021631451257705100421650ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java8.targets; import static org.jacoco.core.test.validation.targets.Stubs.i1; /** * This test target is an interface with a class initializer and default * methods. */ public interface InterfaceDefaultMethodsTarget { public static final int CONST = i1(); // assertFullyCovered() default void m1() { return; // assertFullyCovered() } default void m2() { return; // assertNotCovered() } public class Impl implements InterfaceDefaultMethodsTarget { public Impl() { m1(); } } public static void main(String[] args) { new Impl(); } } InterfaceOnlyDefaultMethodsTarget.java000066400000000000000000000020171451257705100430250ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java8.targets; /** * This test target is an interface with only default methods. */ public interface InterfaceOnlyDefaultMethodsTarget { /* no , only default methods: */ default void m1() { return; // assertFullyCovered() } default void m2() { return; // assertNotCovered() } public class Impl implements InterfaceOnlyDefaultMethodsTarget { public Impl() { m1(); } } public static void main(String[] args) { new Impl(); } } LambdaExpressionsTarget.java000066400000000000000000000020431451257705100410540ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java8.targets; import static org.jacoco.core.test.validation.targets.Stubs.exec; import static org.jacoco.core.test.validation.targets.Stubs.noexec; import static org.jacoco.core.test.validation.targets.Stubs.nop; /** * This test target contains different lambda expressions. */ public class LambdaExpressionsTarget { public static void main(String[] args) { exec(() -> { nop(); // assertFullyCovered() }); noexec(() -> { nop(); // assertNotCovered() }); } } LambdaInInterfaceTarget.java000066400000000000000000000015441451257705100407260ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.java8/src/org/jacoco/core/test/validation/java8/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.java8.targets; import static org.jacoco.core.test.validation.targets.Stubs.nop; /** * This test target builds a constant with a lambda value in an interface. */ public interface LambdaInInterfaceTarget { public static final Runnable RUN = () -> { nop(); // assertFullyCovered() }; } jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/000077500000000000000000000000001451257705100224275ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/.classpath000066400000000000000000000013711451257705100244140ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/.project000066400000000000000000000013571451257705100241040ustar00rootroot00000000000000 org.jacoco.core.test.validation.kotlin org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/pom.xml000066400000000000000000000040021451257705100237400ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.core.test.validation 0.8.11 ../org.jacoco.core.test.validation org.jacoco.core.test.validation.kotlin JaCoCo :: Test :: Core :: Validation Kotlin 1.5.0 ${project.groupId} org.jacoco.core.test org.jetbrains.kotlin kotlin-stdlib ${kotlin.version} org.jetbrains.kotlinx kotlinx-coroutines-core 1.0.1 org.jetbrains.kotlin kotlin-maven-plugin ${kotlin.version} compile process-sources compile jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/000077500000000000000000000000001451257705100232165ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/000077500000000000000000000000001451257705100240055ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/000077500000000000000000000000001451257705100252435ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/000077500000000000000000000000001451257705100261735ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/000077500000000000000000000000001451257705100271525ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/000077500000000000000000000000001451257705100313045ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/000077500000000000000000000000001451257705100326045ustar00rootroot00000000000000KotlinCallableReferenceTest.java000066400000000000000000000016441451257705100407340ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinCallableReferenceTarget; /** * Test of callable references. */ public class KotlinCallableReferenceTest extends ValidationTestBase { public KotlinCallableReferenceTest() { super(KotlinCallableReferenceTarget.class); } } KotlinControlStructuresTest.java000066400000000000000000000016531451257705100411420ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinControlStructuresTarget; /** * Tests of Kotlin control structures. */ public class KotlinControlStructuresTest extends ValidationTestBase { public KotlinControlStructuresTest() { super(KotlinControlStructuresTarget.class); } } KotlinCoroutineTest.java000066400000000000000000000015731451257705100373660ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinCoroutineTarget; /** * Test of coroutines. */ public class KotlinCoroutineTest extends ValidationTestBase { public KotlinCoroutineTest() { super(KotlinCoroutineTarget.class); } } KotlinDataClassTest.java000066400000000000000000000016141451257705100372520ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Fabian Mastenbroek - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinDataClassTarget; /** * Test of data classes. */ public class KotlinDataClassTest extends ValidationTestBase { public KotlinDataClassTest() { super(KotlinDataClassTarget.class); } } KotlinDefaultArgumentsTest.java000066400000000000000000000016551451257705100406720ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinDefaultArgumentsTarget; /** * Test of functions with default arguments. */ public class KotlinDefaultArgumentsTest extends ValidationTestBase { public KotlinDefaultArgumentsTest() { super(KotlinDefaultArgumentsTarget.class); } } KotlinDefaultMethodsTest.java000066400000000000000000000021521451257705100403210ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinDefaultMethodsTarget; /** * Test of code coverage in {@link KotlinDefaultMethodsTarget}. */ public class KotlinDefaultMethodsTest extends ValidationTestBase { public KotlinDefaultMethodsTest() { super(KotlinDefaultMethodsTarget.class); } @Override public void all_missed_instructions_should_have_line_number() { // instructions without line numbers // corresponding to non-executed default implementations } } KotlinDelegatesTest.java000066400000000000000000000016371451257705100373150ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinDelegatesTarget; /** * Test of code coverage in {@link KotlinDelegatesTarget}. */ public class KotlinDelegatesTest extends ValidationTestBase { public KotlinDelegatesTest() { super(KotlinDelegatesTarget.class); } } KotlinElvisOperatorTest.java000066400000000000000000000016171451257705100402140ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinElvisOperatorTarget; /** * Test of elvis operator. */ public class KotlinElvisOperatorTest extends ValidationTestBase { public KotlinElvisOperatorTest() { super(KotlinElvisOperatorTarget.class); } } KotlinInlineTest.java000066400000000000000000000020261451257705100366270ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinInlineTargetKt; /** * Test of inline functions. */ public class KotlinInlineTest extends ValidationTestBase { public KotlinInlineTest() { super(KotlinInlineTargetKt.class); } @Override public void all_missed_instructions_should_have_line_number() { // missed instructions without line number in inline function } } KotlinLambdaExpressionsTest.java000066400000000000000000000017071451257705100410410ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinLambdaExpressionsTarget; /** * Test of code coverage in {@link KotlinLambdaExpressionsTarget}. */ public class KotlinLambdaExpressionsTest extends ValidationTestBase { public KotlinLambdaExpressionsTest() { super(KotlinLambdaExpressionsTarget.class); } } KotlinLateinitTest.java000066400000000000000000000016171451257705100371670ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Fabian Mastenbroek - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinLateinitTarget; /** * Test of lateinit properties. */ public class KotlinLateinitTest extends ValidationTestBase { public KotlinLateinitTest() { super(KotlinLateinitTarget.class); } } KotlinNotNullOperatorTest.java000066400000000000000000000016441451257705100405250ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinNotNullOperatorTarget; /** * Test of not-null assertion operator. */ public class KotlinNotNullOperatorTest extends ValidationTestBase { public KotlinNotNullOperatorTest() { super(KotlinNotNullOperatorTarget.class); } } KotlinSafeCallOperatorTest.java000066400000000000000000000016371451257705100406060ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinSafeCallOperatorTarget; /** * Test of safe call operator. */ public class KotlinSafeCallOperatorTest extends ValidationTestBase { public KotlinSafeCallOperatorTest() { super(KotlinSafeCallOperatorTarget.class); } } KotlinSafeCastTest.java000066400000000000000000000017221451257705100371040ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinElvisOperatorTarget; import org.jacoco.core.test.validation.kotlin.targets.KotlinSafeCastTarget; /** * Test of "safe" cast operator. */ public class KotlinSafeCastTest extends ValidationTestBase { public KotlinSafeCastTest() { super(KotlinSafeCastTarget.class); } } KotlinTopLevelFunctionTest.java000066400000000000000000000016431451257705100406550ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinTopLevelFunctionTargetKt; /** * Test of top level function. */ public class KotlinTopLevelFunctionTest extends ValidationTestBase { public KotlinTopLevelFunctionTest() { super(KotlinTopLevelFunctionTargetKt.class); } } KotlinUnsafeCastOperatorTest.java000066400000000000000000000016531451257705100411660ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinUnsafeCastOperatorTarget; /** * Test of "unsafe" cast operator. */ public class KotlinUnsafeCastOperatorTest extends ValidationTestBase { public KotlinUnsafeCastOperatorTest() { super(KotlinUnsafeCastOperatorTarget.class); } } KotlinWhenExpressionTest.java000066400000000000000000000016421451257705100403750ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.kotlin.targets.KotlinWhenExpressionTarget; /** * Test of when expressions. */ public class KotlinWhenExpressionTest extends ValidationTestBase { public KotlinWhenExpressionTest() { super(KotlinWhenExpressionTarget.class); } } targets/000077500000000000000000000000001451257705100341765ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlinKotlinCallableReferenceTarget.kt000066400000000000000000000020071451257705100424030ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets import org.jacoco.core.test.validation.targets.Stubs.nop /** * Test target for callable references. */ object KotlinCallableReferenceTarget { @JvmStatic fun main(args: Array) { /* Since Kotlin 1.3.30 anonymous class generated for callable reference is marked as synthetic https://youtrack.jetbrains.com/issue/KT-28453 */ nop(::main) // assertFullyCovered(0, 0) } } KotlinControlStructuresTarget.kt000066400000000000000000000070721451257705100426200ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets import org.jacoco.core.test.validation.targets.Stubs.* /** * Test target for Kotlin control structures. */ object KotlinControlStructuresTarget { private fun unconditionalExecution() { nop() // assertFullyCovered() } private fun missedIfBlock() { if (f()) { // assertFullyCovered(1, 1) nop() // assertNotCovered() } else { nop() // assertFullyCovered() } } private fun executedIfBlock() { if (t()) { // assertFullyCovered(1, 1) nop() // assertFullyCovered() } else { nop() // assertNotCovered() } } private fun missedWhileBlock() { while (f()) { // assertFullyCovered(1, 1) nop() // assertNotCovered() } } private fun executedWhileBlock() { var i = 0 while (i++ < 3) { // assertFullyCovered(0, 2) nop() // assertFullyCovered() } } private fun executedDoWhileBlock() { do { nop() // assertFullyCovered() } while (f()) // assertFullyCovered(1, 1) } private fun missedForBlock() { for (j in i2()..i1()) { // assertPartlyCovered(3, 1) nop() // assertNotCovered() } } private fun executedForBlock() { for (j in i1()..i2()) { // assertFullyCovered(1, 3) nop() // assertFullyCovered() } } private fun missedForEachBlock() { for (o in emptyList()) { // assertPartlyCovered(1, 1) nop(o) // assertNotCovered() } } private fun executedForEachBlock() { for (o in setOf(Any())) { // assertFullyCovered(0,2) nop(o) // assertFullyCovered() } } private fun whenExpression() { when (i2()) { // assertFullyCovered(2, 1) 1 -> nop() // assertNotCovered() 2 -> nop() // assertFullyCovered() else -> nop() // assertNotCovered() } } private fun breakStatement() { while (true) { if (t()) { break // assertFullyCovered() } nop() // assertNotCovered() } } private fun continueStatement() { for (j in i1()..i2()) { if (t()) { continue // assertFullyCovered() } nop() // assertNotCovered() } } private fun implicitReturn() { } // assertFullyCovered() private fun explicitReturn() { return // assertFullyCovered() } // assertEmpty() @JvmStatic fun main(args: Array) { unconditionalExecution() missedIfBlock() executedIfBlock() missedWhileBlock() executedWhileBlock() executedDoWhileBlock() missedForBlock() executedForBlock() missedForEachBlock() executedForEachBlock() whenExpression() breakStatement() continueStatement() implicitReturn() explicitReturn() } } KotlinCoroutineTarget.kt000066400000000000000000000031401451257705100410330ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets import kotlinx.coroutines.runBlocking import org.jacoco.core.test.validation.targets.Stubs.nop /** * Test target for coroutines. */ object KotlinCoroutineTarget { private suspend fun suspendingFunction() { // assertEmpty() anotherSuspendingFunction() // assertFullyCovered() nop() // assertFullyCovered() } // assertFullyCovered() private suspend fun suspendingFunctionWithTailCallOptimization() { // assertEmpty() nop() // assertFullyCovered() anotherSuspendingFunction() // assertFullyCovered() } // assertFullyCovered() private suspend fun anotherSuspendingFunction() { nop() // assertFullyCovered() } @JvmStatic fun main(args: Array) { runBlocking { // assertFullyCovered() val x = 42 nop(x) // assertFullyCovered() suspendingFunction() // assertFullyCovered() nop(x) // assertFullyCovered() suspendingFunctionWithTailCallOptimization() } // assertFullyCovered() } } KotlinDataClassTarget.kt000066400000000000000000000033031451257705100407240ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Fabian Mastenbroek - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets import org.jacoco.core.test.validation.targets.Stubs.nop /** * This test target is `data class`. */ object KotlinDataClassTarget { data class DataClass( // assertFullyCovered() val valNoRead: Int, // assertPartlyCovered() val valRead: Int, // assertFullyCovered() var varNoReadNoWrite: Int, // assertPartlyCovered() var varNoWrite: Int, // assertPartlyCovered() var varNoRead: Int, // assertPartlyCovered() var varReadWrite: Int // assertFullyCovered() ) // assertEmpty() data class DataClassOverrideNotCovered(val v: Int) { override fun toString(): String = "" // assertNotCovered() } data class DataClassOverrideCovered(val v: Int) { override fun toString(): String = "" // assertFullyCovered() } @JvmStatic fun main(args: Array) { val d = DataClass(0, 0, 0, 0, 0, 0) nop(d.valRead) nop(d.varNoWrite) d.varNoRead = 1 nop(d.varReadWrite) d.varReadWrite = 1 DataClassOverrideNotCovered(0) DataClassOverrideCovered(0).toString() } } KotlinDefaultArgumentsTarget.kt000066400000000000000000000030071451257705100423400ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets /** * Test target for functions with default arguments. */ object KotlinDefaultArgumentsTarget { private fun f(a: String = "a", b: String = "b") { // assertFullyCovered(0, 0) } private fun longParameter(x: Long = 0) { // assertFullyCovered() } private fun branch(a: Boolean, b: String = if (a) "a" else "b") { // assertFullyCovered(0, 2) } open class Open { open fun f(a: String = "a") { // assertFullyCovered() } } class Constructor() { constructor(a: Boolean, b: String = if (a) "a" else "b") : this() // assertFullyCovered(0, 2) } @JvmStatic fun main(args: Array) { f(a = "a") f(b = "b") /* next invocation doesn't use synthetic method: */ f("a", "b") longParameter() longParameter(1) branch(false) branch(true) Open().f() Constructor(false) Constructor(true) } } KotlinDefaultMethodsTarget.kt000066400000000000000000000020711451257705100417760ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets /** * This test target contains class implementing interface with default methods. */ object KotlinDefaultMethodsTarget { interface I { fun m1() = Unit // assertNotCovered() fun m2() = Unit // assertFullyCovered() fun m3() = Unit // assertNotCovered() } class C : I { // assertFullyCovered() override fun m1() = Unit // assertFullyCovered() } @JvmStatic fun main(args: Array) { C().m1() C().m2() } } KotlinDelegatesTarget.kt000066400000000000000000000015111451257705100407610ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets /** * This test target contains different delegates. */ object KotlinDelegatesTarget { class DelegatedList : List by ArrayList() // assertFullyCovered() @JvmStatic fun main(args: Array) { DelegatedList() } } KotlinElvisOperatorTarget.kt000066400000000000000000000015541451257705100416710ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets /** * Test target for elvis operator. */ object KotlinElvisOperatorTarget { private fun example(x: String?): String { return x ?: "" // assertFullyCovered(0, 2) } @JvmStatic fun main(args: Array) { example("") example(null) } } KotlinInlineTarget.kt000066400000000000000000000023721451257705100403100ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets import org.jacoco.core.test.validation.targets.Stubs.nop import org.jacoco.core.test.validation.targets.Stubs.t /** * Test target for `inline` functions. */ fun main(args: Array) { KotlinInlineTarget.main(args) } inline fun inlined_top_level() { nop() // assertNotCovered() } object KotlinInlineTarget { inline fun inlined() { nop() // assertNotCovered() } @JvmStatic fun main(args: Array) { inlined_top_level() // assertFullyCovered() inlined() // assertFullyCovered() /* Following inlined method for some reasons doesn't appear in SMAP: */ assert(t()) // assertPartlyCovered(2, 2) } } KotlinLambdaExpressionsTarget.kt000066400000000000000000000021101451257705100425030ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets import org.jacoco.core.test.validation.targets.Stubs.* /** * This test target contains different lambda expressions. */ object KotlinLambdaExpressionsTarget { @JvmStatic fun main(args: Array) { exec { // assertFullyCovered() nop() // assertFullyCovered() } // assertFullyCovered() noexec { // assertFullyCovered() nop() // assertNotCovered() } // assertNotCovered() noexec { nop() } // assertPartlyCovered() } } KotlinLateinitTarget.kt000066400000000000000000000015621451257705100406430ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Fabian Mastenbroek - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets import org.jacoco.core.test.validation.targets.Stubs.nop /** * This test target is `lateinit` property. */ object KotlinLateinitTarget { private lateinit var x: String @JvmStatic fun main(args: Array) { x = "" nop(x) // assertFullyCovered() } } KotlinNotNullOperatorTarget.kt000066400000000000000000000016771451257705100422100ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets /** * Test target for not-null assertion operator. */ object KotlinNotNullOperatorTarget { private fun example(x: String?): Int { return x!!.length // assertFullyCovered() } @JvmStatic fun main(args: Array) { example("") try { example(null) } catch (e: NullPointerException) { } } } KotlinSafeCallOperatorTarget.kt000066400000000000000000000015631451257705100422610ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets /** * Test target for safe call operator. */ object KotlinSafeCallOperatorTarget { private fun example(x: String?): Int? { return x?.length // assertFullyCovered(0, 2) } @JvmStatic fun main(args: Array) { example("") example(null) } } KotlinSafeCastTarget.kt000066400000000000000000000015551451257705100405650ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets /** * Test target for "safe" cast operator. */ object KotlinSafeCastTarget { private fun example(x: Any?): String? { return x as? String // assertFullyCovered(0, 2) } @JvmStatic fun main(args: Array) { example("") example(1) } } KotlinTopLevelFunctionTarget.kt000066400000000000000000000012741451257705100423320ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets /** * This test target is top level function. */ fun main(args: Array) { } // assertFullyCovered() KotlinUnsafeCastOperatorTarget.kt000066400000000000000000000015371451257705100426440ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets /** * This test target is "unsafe" cast operator. */ object KotlinUnsafeCastOperatorTarget { private fun nullable(): String? { return "" } @JvmStatic fun main(args: Array) { nullable() as String // assertFullyCovered() } } KotlinWhenExpressionTarget.kt000066400000000000000000000071531451257705100420550ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.kotlin/src/org/jacoco/core/test/validation/kotlin/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.kotlin.targets /** * This test target is `when` expression. */ object KotlinWhenExpressionTarget { private sealed class Sealed { object Sealed1 : Sealed() object Sealed2 : Sealed() } private fun whenSealed(p: Sealed): Int = when (p) { // assertFullyCovered() is Sealed.Sealed1 -> 1 // assertFullyCovered(0, 2) is Sealed.Sealed2 -> 2 // assertFullyCovered() } // assertFullyCovered() @Suppress("REDUNDANT_ELSE_IN_WHEN") private fun whenSealedRedundantElse(p: Sealed): Int = when (p) { // assertFullyCovered() is Sealed.Sealed1 -> 1 // assertFullyCovered(0, 2) is Sealed.Sealed2 -> 2 // assertFullyCovered(0, 0) else -> throw NoWhenBranchMatchedException() // assertEmpty() } // assertFullyCovered() private enum class Enum { A, B } private fun whenEnum(p: Enum): Int = when (p) { // assertFullyCovered(0, 2) Enum.A -> 1 // assertFullyCovered() Enum.B -> 2 // assertFullyCovered() } // assertFullyCovered() @Suppress("REDUNDANT_ELSE_IN_WHEN") private fun whenEnumRedundantElse(p: Enum): Int = when (p) { // assertFullyCovered(0, 2) Enum.A -> 1 // assertFullyCovered() Enum.B -> 2 // assertFullyCovered() else -> throw NoWhenBranchMatchedException() // assertEmpty() } // assertFullyCovered() private fun whenString(p: String): Int = when (p) { // assertFullyCovered(0, 7) "a" -> 1 // assertFullyCovered() "b" -> 2 // assertFullyCovered() "c" -> 3 // assertFullyCovered() "\u0000a" -> 4 // assertFullyCovered() "\u0000b" -> 5 // assertFullyCovered() "\u0000c" -> 6 // assertFullyCovered() else -> 7 // assertFullyCovered() } // assertFullyCovered() /** * Unlike [whenString] * in this example first case is the only case with biggest hashCode value. */ private fun whenStringBiggestHashCodeFirst(p: String): Int = when (p) { // assertFullyCovered(0, 6) "c" -> 1 // assertFullyCovered() "b" -> 2 // assertFullyCovered() "\u0000b" -> 3 // assertFullyCovered() "a" -> 4 // assertFullyCovered() "\u0000a" -> 5 // assertFullyCovered() else -> 6 // assertFullyCovered() } // assertFullyCovered() @JvmStatic fun main(args: Array) { whenSealed(Sealed.Sealed1) whenSealed(Sealed.Sealed2) whenSealedRedundantElse(Sealed.Sealed1) whenSealedRedundantElse(Sealed.Sealed2) whenEnum(Enum.A) whenEnum(Enum.B) whenEnumRedundantElse(Enum.A) whenEnumRedundantElse(Enum.B) whenString("") whenString("a") whenString("b") whenString("c") whenString("\u0000a") whenString("\u0000b") whenString("\u0000c") whenStringBiggestHashCodeFirst("") whenStringBiggestHashCodeFirst("a") whenStringBiggestHashCodeFirst("b") whenStringBiggestHashCodeFirst("c") whenStringBiggestHashCodeFirst("\u0000a") whenStringBiggestHashCodeFirst("\u0000b") } } jacoco-0.8.11/org.jacoco.core.test.validation.scala/000077500000000000000000000000001451257705100222125ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/.classpath000066400000000000000000000013671451257705100242040ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.core.test.validation.scala/.project000066400000000000000000000013561451257705100236660ustar00rootroot00000000000000 org.jacoco.core.test.validation.scala org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.jdt.core.javanature org.eclipse.m2e.core.maven2Nature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.core.test.validation.scala/pom.xml000066400000000000000000000035011451257705100235260ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.core.test.validation 0.8.11 ../org.jacoco.core.test.validation org.jacoco.core.test.validation.scala JaCoCo :: Test :: Core :: Validation Scala 2.13.4 ${project.groupId} org.jacoco.core.test org.scala-lang scala-library ${scala.version} net.alchim31.maven scala-maven-plugin 4.4.0 compile process-sources compile jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/000077500000000000000000000000001451257705100230015ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/org/000077500000000000000000000000001451257705100235705ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/org/jacoco/000077500000000000000000000000001451257705100250265ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/org/jacoco/core/000077500000000000000000000000001451257705100257565ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/org/jacoco/core/test/000077500000000000000000000000001451257705100267355ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/org/jacoco/core/test/validation/000077500000000000000000000000001451257705100310675ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/org/jacoco/core/test/validation/scala/000077500000000000000000000000001451257705100321525ustar00rootroot00000000000000ScalaAnonymousFunctionTest.java000066400000000000000000000016361451257705100402460ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/org/jacoco/core/test/validation/scala/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.scala; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.scala.targets.ScalaAnonymousFunctionTarget; /** * Test of anonymous functions. */ public class ScalaAnonymousFunctionTest extends ValidationTestBase { public ScalaAnonymousFunctionTest() { super(ScalaAnonymousFunctionTarget.class); } } ScalaSingletonObjectTest.java000066400000000000000000000016231451257705100376350ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/org/jacoco/core/test/validation/scala/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.scala; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.scala.targets.ScalaSingletonObjectTarget; /** * Test of singleton object. */ public class ScalaSingletonObjectTest extends ValidationTestBase { public ScalaSingletonObjectTest() { super(ScalaSingletonObjectTarget.class); } } ScalaSynchronizedTest.java000066400000000000000000000016111451257705100372200ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/org/jacoco/core/test/validation/scala/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.scala; import org.jacoco.core.test.validation.ValidationTestBase; import org.jacoco.core.test.validation.scala.targets.ScalaSynchronizedTarget; /** * Test of synchronized block. */ public class ScalaSynchronizedTest extends ValidationTestBase { public ScalaSynchronizedTest() { super(ScalaSynchronizedTarget.class); } } targets/000077500000000000000000000000001451257705100335445ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/org/jacoco/core/test/validation/scalaScalaAnonymousFunctionTarget.scala000066400000000000000000000016331451257705100423650ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/org/jacoco/core/test/validation/scala/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.scala.targets import org.jacoco.core.test.validation.targets.Stubs.{exec, noexec, nop} /** * Test target for anonymous functions. */ object ScalaAnonymousFunctionTarget { def main(args: Array[String]): Unit = { exec(() => { nop() // assertFullyCovered() }) noexec(() => { nop() // assertNotCovered() }) } } ScalaSingletonObjectTarget.scala000066400000000000000000000014261451257705100417600ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/org/jacoco/core/test/validation/scala/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.scala.targets /** * This test target is singleton object. */ object ScalaSingletonObjectTarget { // assertFullyCovered() def main(args: Array[String]): Unit = { // assertFullyCovered() } // assertEmpty() } ScalaSynchronizedTarget.scala000066400000000000000000000017501451257705100413460ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation.scala/src/org/jacoco/core/test/validation/scala/targets/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.scala.targets import org.jacoco.core.test.validation.targets.Stubs.nop /** * Test target for synchronized block. */ object ScalaSynchronizedTarget { private val lock: Object = new Object() def main(args: Array[String]): Unit = { nop() lock.synchronized { // assertFullyCovered() /* Without filter next line covered partly */ nop() // assertFullyCovered() } // assertEmpty() nop() } } jacoco-0.8.11/org.jacoco.core.test.validation/000077500000000000000000000000001451257705100211305ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test.validation/.project000066400000000000000000000011021451257705100225710ustar00rootroot00000000000000 org.jacoco.core.test.validation org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature .settings 2 PARENT-1-PROJECT_LOC/org.jacoco.core.test/.settings jacoco-0.8.11/org.jacoco.core.test.validation/pom.xml000066400000000000000000000431271451257705100224540ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.tests 0.8.11 ../org.jacoco.tests org.jacoco.core.test.validation pom JaCoCo :: Test :: Core :: Validation ../org.jacoco.core.test.validation.java5 true 1.6 1.8 java5-bytecode bytecode.version 5 jdk5 jdk.version 5 java6-bytecode bytecode.version 6 1.6 ../org.jacoco.core.test.validation.kotlin jdk6 jdk.version 6 ../org.jacoco.core.test.validation.kotlin java7-bytecode bytecode.version 7 1.6 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 jdk7 jdk.version 7 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 default true ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.groovy ../org.jacoco.core.test.validation.scala java8-bytecode bytecode.version 8 1.8 1.8 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.groovy ../org.jacoco.core.test.validation.scala java9-bytecode bytecode.version 9 9 9 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.groovy java10-bytecode bytecode.version 10 10 10 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.groovy java11-bytecode bytecode.version 11 11 11 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.groovy ../org.jacoco.core.test.validation.scala java12-bytecode bytecode.version 12 12 12 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.groovy ../org.jacoco.core.test.validation.scala java14-bytecode bytecode.version 14 14 14 14 14 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.java14 ../org.jacoco.core.test.validation.groovy ../org.jacoco.core.test.validation.scala java15-bytecode bytecode.version 15 15 15 15 15 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.java14 ../org.jacoco.core.test.validation.groovy ../org.jacoco.core.test.validation.scala java16-bytecode bytecode.version 16 16 16 16 16 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.java14 ../org.jacoco.core.test.validation.java16 ../org.jacoco.core.test.validation.groovy ../org.jacoco.core.test.validation.scala java17-bytecode bytecode.version 17 16 17 17 17 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.java14 ../org.jacoco.core.test.validation.java16 ../org.jacoco.core.test.validation.groovy ../org.jacoco.core.test.validation.scala java18-bytecode bytecode.version 18 16 16 18 18 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.java14 ../org.jacoco.core.test.validation.java16 ../org.jacoco.core.test.validation.groovy ../org.jacoco.core.test.validation.scala java19-bytecode bytecode.version 19 16 16 19 19 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.java14 ../org.jacoco.core.test.validation.java16 ../org.jacoco.core.test.validation.groovy ../org.jacoco.core.test.validation.scala java20-bytecode bytecode.version 20 16 16 20 20 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.java14 ../org.jacoco.core.test.validation.java16 ../org.jacoco.core.test.validation.groovy ../org.jacoco.core.test.validation.scala java21-bytecode bytecode.version 21 16 16 21 21 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.java14 ../org.jacoco.core.test.validation.java16 ../org.jacoco.core.test.validation.java21 ../org.jacoco.core.test.validation.groovy java22-bytecode bytecode.version 22 16 16 22 22 ../org.jacoco.core.test.validation.kotlin ../org.jacoco.core.test.validation.java7 ../org.jacoco.core.test.validation.java8 ../org.jacoco.core.test.validation.java14 ../org.jacoco.core.test.validation.java16 ../org.jacoco.core.test.validation.java21 jacoco-0.8.11/org.jacoco.core.test/000077500000000000000000000000001451257705100167775ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/.classpath000066400000000000000000000013671451257705100207710ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.core.test/.project000066400000000000000000000010741451257705100204500ustar00rootroot00000000000000 org.jacoco.core.test org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature jacoco-0.8.11/org.jacoco.core.test/.settings/000077500000000000000000000000001451257705100207155ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/.settings/org.eclipse.core.resources.prefs000066400000000000000000000001541451257705100271300ustar00rootroot00000000000000eclipse.preferences.version=1 encoding/src/test/resources=UTF-8 encoding/=UTF-8 encoding/src=UTF-8 jacoco-0.8.11/org.jacoco.core.test/.settings/org.eclipse.jdt.core.prefs000066400000000000000000000641711451257705100257100ustar00rootroot00000000000000#Sat Sep 05 17:52:24 CEST 2009 eclipse.preferences.version=1 org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.5 org.eclipse.jdt.core.compiler.codegen.unusedLocal=preserve org.eclipse.jdt.core.compiler.compliance=1.5 org.eclipse.jdt.core.compiler.debug.lineNumber=generate org.eclipse.jdt.core.compiler.debug.localVariable=generate org.eclipse.jdt.core.compiler.debug.sourceFile=generate org.eclipse.jdt.core.compiler.problem.annotationSuperInterface=warning org.eclipse.jdt.core.compiler.problem.assertIdentifier=error org.eclipse.jdt.core.compiler.problem.autoboxing=warning org.eclipse.jdt.core.compiler.problem.deprecation=warning org.eclipse.jdt.core.compiler.problem.deprecationInDeprecatedCode=disabled org.eclipse.jdt.core.compiler.problem.deprecationWhenOverridingDeprecatedMethod=disabled org.eclipse.jdt.core.compiler.problem.discouragedReference=warning org.eclipse.jdt.core.compiler.problem.emptyStatement=ignore org.eclipse.jdt.core.compiler.problem.enumIdentifier=error org.eclipse.jdt.core.compiler.problem.fallthroughCase=ignore org.eclipse.jdt.core.compiler.problem.fatalOptionalError=enabled org.eclipse.jdt.core.compiler.problem.fieldHiding=ignore org.eclipse.jdt.core.compiler.problem.finalParameterBound=warning org.eclipse.jdt.core.compiler.problem.finallyBlockNotCompletingNormally=warning org.eclipse.jdt.core.compiler.problem.forbiddenReference=error org.eclipse.jdt.core.compiler.problem.hiddenCatchBlock=warning org.eclipse.jdt.core.compiler.problem.incompatibleNonInheritedInterfaceMethod=warning org.eclipse.jdt.core.compiler.problem.incompleteEnumSwitch=ignore org.eclipse.jdt.core.compiler.problem.indirectStaticAccess=ignore org.eclipse.jdt.core.compiler.problem.localVariableHiding=ignore org.eclipse.jdt.core.compiler.problem.methodWithConstructorName=warning org.eclipse.jdt.core.compiler.problem.missingDeprecatedAnnotation=ignore org.eclipse.jdt.core.compiler.problem.missingOverrideAnnotation=error org.eclipse.jdt.core.compiler.problem.missingSerialVersion=warning org.eclipse.jdt.core.compiler.problem.noEffectAssignment=warning org.eclipse.jdt.core.compiler.problem.noImplicitStringConversion=warning org.eclipse.jdt.core.compiler.problem.nonExternalizedStringLiteral=ignore org.eclipse.jdt.core.compiler.problem.nullReference=warning org.eclipse.jdt.core.compiler.problem.overridingPackageDefaultMethod=warning org.eclipse.jdt.core.compiler.problem.parameterAssignment=ignore org.eclipse.jdt.core.compiler.problem.possibleAccidentalBooleanAssignment=ignore org.eclipse.jdt.core.compiler.problem.potentialNullReference=ignore org.eclipse.jdt.core.compiler.problem.rawTypeReference=warning org.eclipse.jdt.core.compiler.problem.redundantNullCheck=ignore org.eclipse.jdt.core.compiler.problem.redundantSuperinterface=ignore org.eclipse.jdt.core.compiler.problem.specialParameterHidingField=disabled org.eclipse.jdt.core.compiler.problem.staticAccessReceiver=warning org.eclipse.jdt.core.compiler.problem.suppressWarnings=enabled org.eclipse.jdt.core.compiler.problem.syntheticAccessEmulation=ignore org.eclipse.jdt.core.compiler.problem.typeParameterHiding=warning org.eclipse.jdt.core.compiler.problem.uncheckedTypeOperation=warning org.eclipse.jdt.core.compiler.problem.undocumentedEmptyBlock=ignore org.eclipse.jdt.core.compiler.problem.unhandledWarningToken=warning org.eclipse.jdt.core.compiler.problem.unnecessaryElse=ignore org.eclipse.jdt.core.compiler.problem.unnecessaryTypeCheck=ignore org.eclipse.jdt.core.compiler.problem.unqualifiedFieldAccess=ignore org.eclipse.jdt.core.compiler.problem.unusedDeclaredThrownException=ignore org.eclipse.jdt.core.compiler.problem.unusedDeclaredThrownExceptionExemptExceptionAndThrowable=enabled org.eclipse.jdt.core.compiler.problem.unusedDeclaredThrownExceptionIncludeDocCommentReference=enabled org.eclipse.jdt.core.compiler.problem.unusedDeclaredThrownExceptionWhenOverriding=disabled org.eclipse.jdt.core.compiler.problem.unusedImport=warning org.eclipse.jdt.core.compiler.problem.unusedLabel=warning org.eclipse.jdt.core.compiler.problem.unusedLocal=warning org.eclipse.jdt.core.compiler.problem.unusedParameter=ignore org.eclipse.jdt.core.compiler.problem.unusedParameterIncludeDocCommentReference=enabled org.eclipse.jdt.core.compiler.problem.unusedParameterWhenImplementingAbstract=disabled org.eclipse.jdt.core.compiler.problem.unusedParameterWhenOverridingConcrete=disabled org.eclipse.jdt.core.compiler.problem.unusedPrivateMember=warning org.eclipse.jdt.core.compiler.problem.unusedWarningToken=warning org.eclipse.jdt.core.compiler.problem.varargsArgumentNeedCast=warning org.eclipse.jdt.core.compiler.source=1.5 org.eclipse.jdt.core.formatter.align_type_members_on_columns=false org.eclipse.jdt.core.formatter.alignment_for_arguments_in_allocation_expression=16 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_enum_constant=16 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_explicit_constructor_call=16 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_method_invocation=16 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_qualified_allocation_expression=16 org.eclipse.jdt.core.formatter.alignment_for_assignment=0 org.eclipse.jdt.core.formatter.alignment_for_binary_expression=16 org.eclipse.jdt.core.formatter.alignment_for_compact_if=16 org.eclipse.jdt.core.formatter.alignment_for_conditional_expression=80 org.eclipse.jdt.core.formatter.alignment_for_enum_constants=0 org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer=16 org.eclipse.jdt.core.formatter.alignment_for_multiple_fields=16 org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_parameters_in_method_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_selector_in_method_invocation=16 org.eclipse.jdt.core.formatter.alignment_for_superclass_in_type_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_enum_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_type_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_constructor_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_method_declaration=16 org.eclipse.jdt.core.formatter.blank_lines_after_imports=1 org.eclipse.jdt.core.formatter.blank_lines_after_package=1 org.eclipse.jdt.core.formatter.blank_lines_before_field=0 org.eclipse.jdt.core.formatter.blank_lines_before_first_class_body_declaration=0 org.eclipse.jdt.core.formatter.blank_lines_before_imports=1 org.eclipse.jdt.core.formatter.blank_lines_before_member_type=1 org.eclipse.jdt.core.formatter.blank_lines_before_method=1 org.eclipse.jdt.core.formatter.blank_lines_before_new_chunk=1 org.eclipse.jdt.core.formatter.blank_lines_before_package=0 org.eclipse.jdt.core.formatter.blank_lines_between_import_groups=1 org.eclipse.jdt.core.formatter.blank_lines_between_type_declarations=1 org.eclipse.jdt.core.formatter.brace_position_for_annotation_type_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_anonymous_type_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_array_initializer=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_block=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_block_in_case=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_constructor_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_enum_constant=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_enum_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_method_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_switch=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_type_declaration=end_of_line org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_block_comment=false org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_javadoc_comment=false org.eclipse.jdt.core.formatter.comment.format_block_comments=true org.eclipse.jdt.core.formatter.comment.format_header=false org.eclipse.jdt.core.formatter.comment.format_html=true org.eclipse.jdt.core.formatter.comment.format_javadoc_comments=true org.eclipse.jdt.core.formatter.comment.format_line_comments=true org.eclipse.jdt.core.formatter.comment.format_source_code=true org.eclipse.jdt.core.formatter.comment.indent_parameter_description=true org.eclipse.jdt.core.formatter.comment.indent_root_tags=true org.eclipse.jdt.core.formatter.comment.insert_new_line_before_root_tags=insert org.eclipse.jdt.core.formatter.comment.insert_new_line_for_parameter=insert org.eclipse.jdt.core.formatter.comment.line_length=80 org.eclipse.jdt.core.formatter.compact_else_if=true org.eclipse.jdt.core.formatter.continuation_indentation=2 org.eclipse.jdt.core.formatter.continuation_indentation_for_array_initializer=2 org.eclipse.jdt.core.formatter.format_guardian_clause_on_one_line=false org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_annotation_declaration_header=true org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_constant_header=true org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_declaration_header=true org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_type_header=true org.eclipse.jdt.core.formatter.indent_breaks_compare_to_cases=true org.eclipse.jdt.core.formatter.indent_empty_lines=false org.eclipse.jdt.core.formatter.indent_statements_compare_to_block=true org.eclipse.jdt.core.formatter.indent_statements_compare_to_body=true org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_cases=true org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_switch=false org.eclipse.jdt.core.formatter.indentation.size=4 org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_local_variable=insert org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_member=insert org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_parameter=do not insert org.eclipse.jdt.core.formatter.insert_new_line_after_opening_brace_in_array_initializer=do not insert org.eclipse.jdt.core.formatter.insert_new_line_at_end_of_file_if_missing=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_catch_in_try_statement=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_closing_brace_in_array_initializer=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_else_in_if_statement=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_finally_in_try_statement=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_while_in_do_statement=do not insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_annotation_declaration=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_anonymous_type_declaration=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_block=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_constant=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_declaration=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_method_body=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_after_and_in_type_parameter=insert org.eclipse.jdt.core.formatter.insert_space_after_assignment_operator=insert org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation_type_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_after_binary_operator=insert org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_parameters=insert org.eclipse.jdt.core.formatter.insert_space_after_closing_brace_in_block=insert org.eclipse.jdt.core.formatter.insert_space_after_closing_paren_in_cast=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_assert=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_case=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_conditional=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_for=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_labeled_statement=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_allocation_expression=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_annotation=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_array_initializer=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_parameters=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_throws=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_constant_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_declarations=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_explicitconstructorcall_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_increments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_inits=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_parameters=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_throws=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_invocation_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_field_declarations=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_local_declarations=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_parameterized_type_reference=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_superinterfaces=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_parameters=insert org.eclipse.jdt.core.formatter.insert_space_after_ellipsis=insert org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_parameterized_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_brace_in_array_initializer=insert org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_cast=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_catch=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_constructor_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_enum_constant=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_for=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_if=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_invocation=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_parenthesized_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_switch=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_synchronized=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_while=do not insert org.eclipse.jdt.core.formatter.insert_space_after_postfix_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_after_prefix_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_after_question_in_conditional=insert org.eclipse.jdt.core.formatter.insert_space_after_question_in_wildcard=do not insert org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_for=insert org.eclipse.jdt.core.formatter.insert_space_after_unary_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_before_and_in_type_parameter=insert org.eclipse.jdt.core.formatter.insert_space_before_assignment_operator=insert org.eclipse.jdt.core.formatter.insert_space_before_at_in_annotation_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_binary_operator=insert org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_parameterized_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_brace_in_array_initializer=insert org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_cast=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_catch=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_constructor_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_enum_constant=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_for=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_if=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_invocation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_parenthesized_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_switch=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_synchronized=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_while=do not insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_assert=insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_case=do not insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_conditional=insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_default=do not insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_for=insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_labeled_statement=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_array_initializer=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_throws=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_constant_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_declarations=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_explicitconstructorcall_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_increments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_inits=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_throws=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_invocation_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_field_declarations=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_local_declarations=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_parameterized_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_superinterfaces=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_ellipsis=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_parameterized_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_annotation_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_anonymous_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_array_initializer=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_block=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_constructor_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_constant=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_method_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_switch=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation_type_member_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_catch=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_constructor_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_enum_constant=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_for=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_if=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_invocation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_parenthesized_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_switch=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_synchronized=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_while=insert org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_return=insert org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_throw=insert org.eclipse.jdt.core.formatter.insert_space_before_postfix_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_before_prefix_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_before_question_in_conditional=insert org.eclipse.jdt.core.formatter.insert_space_before_question_in_wildcard=do not insert org.eclipse.jdt.core.formatter.insert_space_before_semicolon=do not insert org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_for=do not insert org.eclipse.jdt.core.formatter.insert_space_before_unary_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_between_brackets_in_array_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_braces_in_array_initializer=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_brackets_in_array_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_annotation_type_member_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_constructor_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_enum_constant=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_invocation=do not insert org.eclipse.jdt.core.formatter.keep_else_statement_on_same_line=false org.eclipse.jdt.core.formatter.keep_empty_array_initializer_on_one_line=false org.eclipse.jdt.core.formatter.keep_imple_if_on_one_line=false org.eclipse.jdt.core.formatter.keep_then_statement_on_same_line=false org.eclipse.jdt.core.formatter.lineSplit=80 org.eclipse.jdt.core.formatter.never_indent_block_comments_on_first_column=false org.eclipse.jdt.core.formatter.never_indent_line_comments_on_first_column=false org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_method_body=0 org.eclipse.jdt.core.formatter.number_of_empty_lines_to_preserve=1 org.eclipse.jdt.core.formatter.put_empty_statement_on_new_line=true org.eclipse.jdt.core.formatter.tabulation.char=tab org.eclipse.jdt.core.formatter.tabulation.size=4 org.eclipse.jdt.core.formatter.use_tabs_only_for_leading_indentations=false org.eclipse.jdt.core.formatter.wrap_before_binary_operator=true jacoco-0.8.11/org.jacoco.core.test/.settings/org.eclipse.jdt.ui.prefs000066400000000000000000000061641451257705100253730ustar00rootroot00000000000000eclipse.preferences.version=1 editor_save_participant_org.eclipse.jdt.ui.postsavelistener.cleanup=true formatter_profile=org.eclipse.jdt.ui.default.eclipse_profile formatter_settings_version=11 sp_cleanup.add_default_serial_version_id=true sp_cleanup.add_generated_serial_version_id=false sp_cleanup.add_missing_annotations=true sp_cleanup.add_missing_deprecated_annotations=true sp_cleanup.add_missing_methods=false sp_cleanup.add_missing_nls_tags=false sp_cleanup.add_missing_override_annotations=true sp_cleanup.add_missing_override_annotations_interface_methods=false sp_cleanup.add_serial_version_id=false sp_cleanup.always_use_blocks=true sp_cleanup.always_use_parentheses_in_expressions=false sp_cleanup.always_use_this_for_non_static_field_access=false sp_cleanup.always_use_this_for_non_static_method_access=false sp_cleanup.convert_functional_interfaces=false sp_cleanup.convert_to_enhanced_for_loop=false sp_cleanup.correct_indentation=false sp_cleanup.format_source_code=true sp_cleanup.format_source_code_changes_only=false sp_cleanup.insert_inferred_type_arguments=false sp_cleanup.make_local_variable_final=false sp_cleanup.make_parameters_final=false sp_cleanup.make_private_fields_final=true sp_cleanup.make_type_abstract_if_missing_method=false sp_cleanup.make_variable_declarations_final=true sp_cleanup.never_use_blocks=false sp_cleanup.never_use_parentheses_in_expressions=true sp_cleanup.on_save_use_additional_actions=true sp_cleanup.organize_imports=true sp_cleanup.qualify_static_field_accesses_with_declaring_class=false sp_cleanup.qualify_static_member_accesses_through_instances_with_declaring_class=true sp_cleanup.qualify_static_member_accesses_through_subtypes_with_declaring_class=true sp_cleanup.qualify_static_member_accesses_with_declaring_class=true sp_cleanup.qualify_static_method_accesses_with_declaring_class=false sp_cleanup.remove_private_constructors=true sp_cleanup.remove_redundant_modifiers=false sp_cleanup.remove_redundant_semicolons=false sp_cleanup.remove_redundant_type_arguments=false sp_cleanup.remove_trailing_whitespaces=true sp_cleanup.remove_trailing_whitespaces_all=true sp_cleanup.remove_trailing_whitespaces_ignore_empty=false sp_cleanup.remove_unnecessary_casts=true sp_cleanup.remove_unnecessary_nls_tags=false sp_cleanup.remove_unused_imports=false sp_cleanup.remove_unused_local_variables=false sp_cleanup.remove_unused_private_fields=true sp_cleanup.remove_unused_private_members=false sp_cleanup.remove_unused_private_methods=true sp_cleanup.remove_unused_private_types=true sp_cleanup.sort_members=false sp_cleanup.sort_members_all=false sp_cleanup.use_anonymous_class_creation=false sp_cleanup.use_autoboxing=false sp_cleanup.use_blocks=false sp_cleanup.use_blocks_only_for_return_and_throw=false sp_cleanup.use_lambda=false sp_cleanup.use_parentheses_in_expressions=false sp_cleanup.use_this_for_non_static_field_access=false sp_cleanup.use_this_for_non_static_field_access_only_if_necessary=true sp_cleanup.use_this_for_non_static_method_access=false sp_cleanup.use_this_for_non_static_method_access_only_if_necessary=true sp_cleanup.use_unboxing=false jacoco-0.8.11/org.jacoco.core.test/pom.xml000066400000000000000000000027611451257705100203220ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.tests 0.8.11 ../org.jacoco.tests org.jacoco.core.test JaCoCo :: Test :: Core org.jacoco.core.* ${project.groupId} org.jacoco.core org.ow2.asm asm-analysis org.ow2.asm asm-util junit junit jacoco-0.8.11/org.jacoco.core.test/src/000077500000000000000000000000001451257705100175665ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/000077500000000000000000000000001451257705100203555ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/000077500000000000000000000000001451257705100216135ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/000077500000000000000000000000001451257705100225435ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/JaCoCoTest.java000066400000000000000000000022021451257705100253400ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNotNull; import org.junit.Test; /** * Unit tests for {@link JaCoCo}. */ public class JaCoCoTest { @Test public void testVERSION() { assertNotNull(JaCoCo.VERSION); } @Test public void testCOMMITID() { assertNotNull(JaCoCo.COMMITID); } @Test public void testCOMMITID_SHORT() { assertEquals(7, JaCoCo.COMMITID_SHORT.length()); } @Test public void testHOMEURL() { assertNotNull(JaCoCo.HOMEURL); } @Test public void testRUNTIMEPACKAGE() { assertNotNull(JaCoCo.RUNTIMEPACKAGE); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/analysis/000077500000000000000000000000001451257705100243665ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/analysis/AnalyzerTest.java000066400000000000000000000336111451257705100276620ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; import static org.junit.Assert.assertArrayEquals; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.util.Arrays; import java.util.Collections; import java.util.HashMap; import java.util.HashSet; import java.util.Map; import java.util.zip.GZIPOutputStream; import java.util.zip.ZipEntry; import java.util.zip.ZipInputStream; import java.util.zip.ZipOutputStream; import org.jacoco.core.JaCoCo; import org.jacoco.core.data.ExecutionDataStore; import org.jacoco.core.internal.Pack200Streams; import org.jacoco.core.internal.data.CRC64; import org.jacoco.core.test.TargetLoader; import org.junit.AssumptionViolatedException; import org.junit.Before; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TemporaryFolder; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.Opcodes; /** * Unit tests for {@link Analyzer}. */ public class AnalyzerTest { @Rule public TemporaryFolder folder = new TemporaryFolder(); private Analyzer analyzer; private Map classes; private ExecutionDataStore executionData; private class EmptyStructureVisitor implements ICoverageVisitor { public void visitCoverage(IClassCoverage coverage) { final String name = coverage.getName(); assertNull("Class already processed: " + name, classes.put(name, coverage)); } } @Before public void setup() { classes = new HashMap(); executionData = new ExecutionDataStore(); analyzer = new Analyzer(executionData, new EmptyStructureVisitor()); } @Test public void should_ignore_module_info() throws Exception { final ClassWriter cw = new ClassWriter(0); cw.visit(Opcodes.V9, Opcodes.ACC_MODULE, "module-info", null, null, null); cw.visitModule("module", 0, null).visitEnd(); cw.visitEnd(); final byte[] bytes = cw.toByteArray(); analyzer.analyzeClass(bytes, ""); assertTrue(classes.isEmpty()); } @Test public void should_ignore_synthetic_classes() throws Exception { final ClassWriter cw = new ClassWriter(0); cw.visit(Opcodes.V1_5, Opcodes.ACC_SYNTHETIC, "Foo", null, "java/lang/Object", null); cw.visitEnd(); final byte[] bytes = cw.toByteArray(); analyzer.analyzeClass(bytes, ""); assertTrue(classes.isEmpty()); } @Test public void should_not_modify_class_bytes_to_support_next_version() throws Exception { final byte[] originalBytes = createClass(Opcodes.V21 + 1); final byte[] bytes = new byte[originalBytes.length]; System.arraycopy(originalBytes, 0, bytes, 0, originalBytes.length); final long expectedClassId = CRC64.classId(bytes); analyzer.analyzeClass(bytes, ""); assertArrayEquals(originalBytes, bytes); assertEquals(expectedClassId, classes.get("Foo").getId()); } private static byte[] createClass(final int version) { final ClassWriter cw = new ClassWriter(0); cw.visit(version, 0, "Foo", null, "java/lang/Object", null); cw.visitEnd(); return cw.toByteArray(); } /** * @see #analyzeAll_should_throw_exception_for_unsupported_class_file_version() */ @Test public void analyzeClass_should_throw_exception_for_unsupported_class_file_version() { final byte[] bytes = createClass(Opcodes.V21 + 2); try { analyzer.analyzeClass(bytes, "UnsupportedVersion"); fail("exception expected"); } catch (IOException e) { assertExceptionMessage("UnsupportedVersion", e); assertEquals("Unsupported class file major version 67", e.getCause().getMessage()); } } @Test public void testAnalyzeClassFromStream() throws IOException { analyzer.analyzeClass(TargetLoader.getClassData(AnalyzerTest.class), "Test"); assertClasses("org/jacoco/core/analysis/AnalyzerTest"); } @Test public void testAnalyzeClassFromByteArray() throws IOException { analyzer.analyzeClass( TargetLoader.getClassDataAsBytes(AnalyzerTest.class), "Test"); assertClasses("org/jacoco/core/analysis/AnalyzerTest"); assertFalse(classes.get("org/jacoco/core/analysis/AnalyzerTest") .isNoMatch()); } @Test public void testAnalyzeClassIdMatch() throws IOException { final byte[] bytes = TargetLoader .getClassDataAsBytes(AnalyzerTest.class); executionData.get(Long.valueOf(CRC64.classId(bytes)), "org/jacoco/core/analysis/AnalyzerTest", 400); analyzer.analyzeClass(bytes, "Test"); assertFalse(classes.get("org/jacoco/core/analysis/AnalyzerTest") .isNoMatch()); } @Test public void testAnalyzeClassNoIdMatch() throws IOException { executionData.get(Long.valueOf(0), "org/jacoco/core/analysis/AnalyzerTest", 400); analyzer.analyzeClass( TargetLoader.getClassDataAsBytes(AnalyzerTest.class), "Test"); assertTrue(classes.get("org/jacoco/core/analysis/AnalyzerTest") .isNoMatch()); } @Test public void testAnalyzeClass_Broken() throws IOException { final byte[] brokenclass = TargetLoader .getClassDataAsBytes(AnalyzerTest.class); brokenclass[10] = 0x23; try { analyzer.analyzeClass(brokenclass, "Broken.class"); fail("expected exception"); } catch (IOException e) { assertExceptionMessage("Broken.class", e); } } private static class BrokenInputStream extends InputStream { @Override public int read() throws IOException { throw new IOException(); } } /** * Triggers exception in {@link Analyzer#analyzeClass(InputStream, String)}. */ @Test public void testAnalyzeClass_BrokenStream() throws IOException { try { analyzer.analyzeClass(new BrokenInputStream(), "BrokenStream"); fail("exception expected"); } catch (IOException e) { assertExceptionMessage("BrokenStream", e); } } /** * @see #analyzeClass_should_throw_exception_for_unsupported_class_file_version() */ @Test public void analyzeAll_should_throw_exception_for_unsupported_class_file_version() { final byte[] bytes = createClass(Opcodes.V21 + 2); try { analyzer.analyzeAll(new ByteArrayInputStream(bytes), "UnsupportedVersion"); fail("exception expected"); } catch (IOException e) { assertExceptionMessage("UnsupportedVersion", e); assertEquals("Unsupported class file major version 67", e.getCause().getMessage()); } } @Test public void testAnalyzeAll_Class() throws IOException { final int count = analyzer.analyzeAll( TargetLoader.getClassData(AnalyzerTest.class), "Test"); assertEquals(1, count); assertClasses("org/jacoco/core/analysis/AnalyzerTest"); } @Test public void testAnalyzeAll_Zip() throws IOException { final ByteArrayOutputStream buffer = new ByteArrayOutputStream(); final ZipOutputStream zip = new ZipOutputStream(buffer); zip.putNextEntry( new ZipEntry("org/jacoco/core/analysis/AnalyzerTest.class")); zip.write(TargetLoader.getClassDataAsBytes(AnalyzerTest.class)); zip.finish(); final int count = analyzer.analyzeAll( new ByteArrayInputStream(buffer.toByteArray()), "Test"); assertEquals(1, count); assertClasses("org/jacoco/core/analysis/AnalyzerTest"); } @Test public void testAnalyzeAll_EmptyZipEntry() throws IOException { final ByteArrayOutputStream buffer = new ByteArrayOutputStream(); final ZipOutputStream zip = new ZipOutputStream(buffer); zip.putNextEntry(new ZipEntry("empty.txt")); zip.finish(); final int count = analyzer.analyzeAll( new ByteArrayInputStream(buffer.toByteArray()), "Test"); assertEquals(0, count); } /** * Triggers exception in * {@link Analyzer#analyzeAll(java.io.InputStream, String)}. */ @Test public void testAnalyzeAll_Broken() throws IOException { try { analyzer.analyzeAll(new BrokenInputStream(), "Test"); fail("expected exception"); } catch (IOException e) { assertExceptionMessage("Test", e); } } /** * Triggers exception in * {@link Analyzer#analyzeGzip(java.io.InputStream, String)}. */ @Test public void testAnalyzeAll_BrokenGZ() { final byte[] buffer = new byte[] { 0x1f, (byte) 0x8b, 0x00, 0x00 }; try { analyzer.analyzeAll(new ByteArrayInputStream(buffer), "Test.gz"); fail("expected exception"); } catch (IOException e) { assertExceptionMessage("Test.gz", e); } } @Test public void testAnalyzeAll_Pack200() throws IOException { try { Class.forName("java.util.jar.Pack200"); } catch (ClassNotFoundException e) { throw new AssumptionViolatedException( "this test requires JDK with Pack200"); } final ByteArrayOutputStream zipbuffer = new ByteArrayOutputStream(); final ZipOutputStream zip = new ZipOutputStream(zipbuffer); zip.putNextEntry( new ZipEntry("org/jacoco/core/analysis/AnalyzerTest.class")); zip.write(TargetLoader.getClassDataAsBytes(AnalyzerTest.class)); zip.finish(); final ByteArrayOutputStream pack200buffer = new ByteArrayOutputStream(); GZIPOutputStream gzipOutput = new GZIPOutputStream(pack200buffer); Pack200Streams.pack(zipbuffer.toByteArray(), gzipOutput); gzipOutput.finish(); final int count = analyzer.analyzeAll( new ByteArrayInputStream(pack200buffer.toByteArray()), "Test"); assertEquals(1, count); assertClasses("org/jacoco/core/analysis/AnalyzerTest"); } /** * Triggers exception in * {@link Analyzer#analyzePack200(java.io.InputStream, String)}. */ @Test public void testAnalyzeAll_BrokenPack200() { final byte[] buffer = new byte[] { (byte) 0xca, (byte) 0xfe, (byte) 0xd0, 0x0d }; try { analyzer.analyzeAll(new ByteArrayInputStream(buffer), "Test.pack200"); fail("expected exception"); } catch (IOException e) { assertExceptionMessage("Test.pack200", e); } } @Test public void testAnalyzeAll_Empty() throws IOException { final int count = analyzer .analyzeAll(new ByteArrayInputStream(new byte[0]), "Test"); assertEquals(0, count); assertEquals(Collections.emptyMap(), classes); } @Test public void testAnalyzeAll_Folder() throws IOException { createClassfile("bin1", AnalyzerTest.class); final int count = analyzer.analyzeAll(folder.getRoot()); assertEquals(1, count); assertClasses("org/jacoco/core/analysis/AnalyzerTest"); } @Test public void testAnalyzeAll_Path() throws IOException { createClassfile("bin1", Analyzer.class); createClassfile("bin2", AnalyzerTest.class); String path = "bin1" + File.pathSeparator + "bin2"; final int count = analyzer.analyzeAll(path, folder.getRoot()); assertEquals(2, count); assertClasses("org/jacoco/core/analysis/Analyzer", "org/jacoco/core/analysis/AnalyzerTest"); } /** * Triggers exception in * {@link Analyzer#nextEntry(java.util.zip.ZipInputStream, String)}. */ @Test public void testAnalyzeAll_BrokenZip() { final byte[] buffer = new byte[30]; buffer[0] = 0x50; buffer[1] = 0x4b; buffer[2] = 0x03; buffer[3] = 0x04; Arrays.fill(buffer, 4, buffer.length, (byte) 0x42); try { analyzer.analyzeAll(new ByteArrayInputStream(buffer), "Test.zip"); fail("expected exception"); } catch (IOException e) { assertExceptionMessage("Test.zip", e); } } /** * With JDK 5 triggers exception in * {@link Analyzer#nextEntry(ZipInputStream, String)}, i.e. message will * contain only "broken.zip". * * With JDK > 5 triggers exception in * {@link Analyzer#analyzeAll(java.io.InputStream, String)}, i.e. message * will contain only "broken.zip@brokenentry.txt". */ @Test public void testAnalyzeAll_BrokenZipEntry() throws IOException { File file = new File(folder.getRoot(), "broken.zip"); OutputStream out = new FileOutputStream(file); ZipOutputStream zip = new ZipOutputStream(out); zip.putNextEntry(new ZipEntry("brokenentry.txt")); out.write(0x23); // Unexpected data here zip.close(); try { analyzer.analyzeAll(file); fail("expected exception"); } catch (IOException e) { assertTrue(e.getMessage().startsWith("Error while analyzing")); assertTrue(e.getMessage().contains("broken.zip")); } } /** * Triggers exception in * {@link Analyzer#analyzeClass(java.io.InputStream, String)}. */ @Test public void testAnalyzeAll_BrokenClassFileInZip() throws IOException { final ByteArrayOutputStream buffer = new ByteArrayOutputStream(); final ZipOutputStream zip = new ZipOutputStream(buffer); zip.putNextEntry( new ZipEntry("org/jacoco/core/analysis/AnalyzerTest.class")); final byte[] brokenclass = TargetLoader .getClassDataAsBytes(AnalyzerTest.class); brokenclass[10] = 0x23; zip.write(brokenclass); zip.finish(); try { analyzer.analyzeAll(new ByteArrayInputStream(buffer.toByteArray()), "test.zip"); fail("expected exception"); } catch (IOException e) { assertExceptionMessage( "test.zip@org/jacoco/core/analysis/AnalyzerTest.class", e); } } private void createClassfile(final String dir, final Class source) throws IOException { File file = new File(folder.getRoot(), dir); file.mkdirs(); file = new File(file, "some.class"); OutputStream out = new FileOutputStream(file); out.write(TargetLoader.getClassDataAsBytes(source)); out.close(); } private void assertClasses(String... classNames) { assertEquals(new HashSet(Arrays.asList(classNames)), classes.keySet()); } private void assertExceptionMessage(String name, Exception ex) { String expected = "Error while analyzing " + name + " with JaCoCo " + JaCoCo.VERSION + "/" + JaCoCo.COMMITID_SHORT + "."; assertEquals(expected, ex.getMessage()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/analysis/CounterComparatorTest.java000066400000000000000000000100251451257705100315360ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; import static org.jacoco.core.analysis.ICoverageNode.ElementType.GROUP; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; import java.util.Comparator; import org.jacoco.core.analysis.ICoverageNode.CounterEntity; import org.jacoco.core.internal.analysis.CounterImpl; import org.junit.Test; /** * Unit tests for {@link CounterComparator}. */ public class CounterComparatorTest { @Test public void testTotalItemsComparator() { final Comparator cmp = CounterComparator.TOTALITEMS; assertCmpLess(cmp, 19, 5, 19, 6); assertCmpEquals(cmp, 20, 5, 19, 6); assertCmpGreater(cmp, 21, 5, 19, 6); } @Test public void testCoveredItemsComparator() { final Comparator cmp = CounterComparator.COVEREDITEMS; assertCmpLess(cmp, 73, 7, 42, 8); assertCmpEquals(cmp, 42, 8, 82, 8); assertCmpGreater(cmp, 21, 9, 32, 8); } @Test public void testMissedItemsComparator() { final Comparator cmp = CounterComparator.MISSEDITEMS; assertCmpLess(cmp, 10, 40, 11, 80); assertCmpEquals(cmp, 10, 40, 10, 80); assertCmpGreater(cmp, 11, 39, 10, 80); } @Test public void testCoveredRatioComparator() { final Comparator cmp = CounterComparator.COVEREDRATIO; assertCmpLess(cmp, 25, 25, 44, 46); assertCmpEquals(cmp, 40, 10, 64, 16); assertCmpGreater(cmp, 25, 25, 46, 44); } @Test public void testMissedRatioComparator() { final Comparator cmp = CounterComparator.MISSEDRATIO; assertCmpLess(cmp, 25, 25, 46, 44); assertCmpEquals(cmp, 40, 10, 64, 16); assertCmpGreater(cmp, 25, 25, 44, 46); } @Test public void testReverseComparator() { final Comparator cmp = CounterComparator.TOTALITEMS.reverse(); assertCmpGreater(cmp, 19, 5, 19, 6); assertCmpEquals(cmp, 20, 5, 19, 6); assertCmpLess(cmp, 21, 5, 19, 6); } @Test public void testReverseReverseComparator() { final Comparator cmp = CounterComparator.TOTALITEMS.reverse() .reverse(); assertCmpGreater(cmp, 21, 5, 19, 6); assertCmpEquals(cmp, 20, 5, 19, 6); assertCmpLess(cmp, 19, 5, 19, 6); } @Test public void testNodeComparator1() { ICoverageNode d1 = new MockNode(18); ICoverageNode d2 = new MockNode(15); final Comparator cmp = CounterComparator.TOTALITEMS .on(CounterEntity.INSTRUCTION); assertTrue(cmp.compare(d1, d2) > 0); } @Test public void testNodeComparator2() { ICoverageNode d1 = new MockNode(18); ICoverageNode d2 = new MockNode(15); final Comparator cmp = CounterComparator.TOTALITEMS .on(CounterEntity.LINE); assertEquals(0, cmp.compare(d1, d2), 0.0); } private void assertCmpEquals(Comparator cmp, int missed1, int covered1, int missed2, int covered2) { assertEquals(0, cmp.compare(ctr(missed1, covered1), ctr(missed2, covered2)), 0.0); } private void assertCmpLess(Comparator cmp, int missed1, int covered1, int missed2, int covered2) { assertTrue(cmp.compare(ctr(missed1, covered1), ctr(missed2, covered2)) < 0); } private void assertCmpGreater(Comparator cmp, int missed1, int covered1, int missed2, int covered2) { assertTrue(cmp.compare(ctr(missed1, covered1), ctr(missed2, covered2)) > 0); } private CounterImpl ctr(int missed, int covered) { return CounterImpl.getInstance(missed, covered); } private static final class MockNode extends CoverageNodeImpl { MockNode(int total) { super(GROUP, "mock"); instructionCounter = CounterImpl.getInstance(total, 0); } } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/analysis/CoverageBuilderTest.java000066400000000000000000000231751451257705100311430ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNotNull; import java.util.Arrays; import java.util.Collection; import java.util.Collections; import java.util.HashMap; import java.util.HashSet; import java.util.Map; import java.util.Set; import org.jacoco.core.internal.analysis.ClassCoverageImpl; import org.jacoco.core.internal.analysis.CounterImpl; import org.jacoco.core.internal.analysis.MethodCoverageImpl; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link CoverageBuilder}. */ public class CoverageBuilderTest { private CoverageBuilder coverageBuilder; @Before public void setup() { coverageBuilder = new CoverageBuilder(); } @Test public void testCreateClassMissed() { final MethodCoverageImpl method = new MethodCoverageImpl("doit", "()V", null); method.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 6); method.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 7); method.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 8); method.incrementMethodCounter(); addClass(123L, false, "Sample", null, method); final Collection classes = coverageBuilder.getClasses(); assertEquals(1, classes.size()); IClassCoverage c = classes.iterator().next(); assertEquals("Sample", c.getName()); assertEquals(1, c.getClassCounter().getTotalCount()); assertEquals(0, c.getClassCounter().getCoveredCount()); assertEquals(1, c.getMethodCounter().getTotalCount()); assertEquals(0, c.getMethodCounter().getCoveredCount()); assertEquals(3, c.getLineCounter().getTotalCount()); assertEquals(0, c.getLineCounter().getCoveredCount()); final Collection methods = c.getMethods(); assertEquals(1, methods.size()); IMethodCoverage m = methods.iterator().next(); assertEquals("doit", m.getName()); assertEquals("()V", m.getDesc()); assertEquals(1, m.getMethodCounter().getTotalCount()); assertEquals(0, m.getMethodCounter().getCoveredCount()); assertEquals(3, m.getLineCounter().getTotalCount()); assertEquals(0, m.getLineCounter().getCoveredCount()); } @Test public void testCreateClassCovered() { final MethodCoverageImpl method = new MethodCoverageImpl("doit", "()V", null); method.increment(CounterImpl.COUNTER_0_1, CounterImpl.COUNTER_0_0, 6); method.increment(CounterImpl.COUNTER_0_1, CounterImpl.COUNTER_0_0, 7); method.increment(CounterImpl.COUNTER_0_1, CounterImpl.COUNTER_0_0, 8); method.incrementMethodCounter(); addClass(123L, false, "Sample", null, method); final Collection classes = coverageBuilder.getClasses(); assertEquals(1, classes.size()); IClassCoverage c = classes.iterator().next(); assertEquals("Sample", c.getName()); assertEquals(1, c.getClassCounter().getTotalCount()); assertEquals(1, c.getClassCounter().getCoveredCount()); assertEquals(1, c.getMethodCounter().getTotalCount()); assertEquals(1, c.getMethodCounter().getCoveredCount()); assertEquals(3, c.getLineCounter().getTotalCount()); assertEquals(3, c.getLineCounter().getCoveredCount()); final Collection methods = c.getMethods(); assertEquals(1, methods.size()); IMethodCoverage m = methods.iterator().next(); assertEquals("doit", m.getName()); assertEquals("()V", m.getDesc()); assertEquals(1, m.getMethodCounter().getTotalCount()); assertEquals(1, m.getMethodCounter().getCoveredCount()); assertEquals(3, m.getLineCounter().getTotalCount()); assertEquals(3, m.getLineCounter().getCoveredCount()); } @Test public void should_not_ignore_empty_classes() { addClass(123L, false, "Empty", null); assertEquals(1, coverageBuilder.getClasses().size()); } @Test(expected = IllegalStateException.class) public void testDuplicateClassNameDifferent() { MethodCoverageImpl method = new MethodCoverageImpl("doit", "()V", null); method.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 3); addClass(123L, false, "Sample", null, method); // Add class with different id must fail: method = new MethodCoverageImpl("doit", "()V", null); method.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 3); addClass(345L, false, "Sample", null, method); } @Test public void testDuplicateClassNameIdentical() { MethodCoverageImpl method = new MethodCoverageImpl("doit", "()V", null); method.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 3); addClass(123L, false, "Sample", null, method); // Add class with same id: method = new MethodCoverageImpl("doit", "()V", null); method.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 3); addClass(123L, false, "Sample", null, method); // Second add must be ignored: final Collection classes = coverageBuilder.getClasses(); assertEquals(1, classes.size()); } @Test public void testCreateSourceFile() { final MethodCoverageImpl method1 = new MethodCoverageImpl("doit", "()V", null); method1.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 3); addClass(123L, false, "Sample", "Sample.java", method1); final MethodCoverageImpl method2 = new MethodCoverageImpl("doit", "()V", null); method2.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 6); addClass(234L, false, "Second", "Sample.java", method2); final Collection sourcefiles = coverageBuilder .getSourceFiles(); assertEquals(1, sourcefiles.size()); ISourceFileCoverage s = sourcefiles.iterator().next(); assertEquals(2, s.getClassCounter().getTotalCount()); assertEquals(0, s.getClassCounter().getCoveredCount()); } @Test public void testCreateSourceFileDuplicateClassNameIdentical() { final MethodCoverageImpl method1 = new MethodCoverageImpl("doit", "()V", null); method1.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 3); addClass(123L, false, "Sample", "Sample.java", method1); final MethodCoverageImpl method2 = new MethodCoverageImpl("doit", "()V", null); method2.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 3); addClass(123L, false, "Sample", "Sample.java", method2); final Collection sourcefiles = coverageBuilder .getSourceFiles(); assertEquals(1, sourcefiles.size()); ISourceFileCoverage s = sourcefiles.iterator().next(); assertEquals(1, s.getClassCounter().getTotalCount()); assertEquals(0, s.getClassCounter().getCoveredCount()); } @Test public void testGetBundle() { final MethodCoverageImpl method1 = new MethodCoverageImpl("doit", "()V", null); method1.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 3); addClass(1, false, "org/jacoco/examples/Sample1", null, method1); final MethodCoverageImpl method2 = new MethodCoverageImpl("doit", "()V", null); method2.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 6); addClass(2, false, "org/jacoco/examples/Sample2", null, method2); final MethodCoverageImpl method3 = new MethodCoverageImpl("doit", "()V", null); method3.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 1); addClass(3, false, "Sample3", null, method3); IBundleCoverage bundle = coverageBuilder.getBundle("testbundle"); assertEquals("testbundle", bundle.getName()); final Collection packages = bundle.getPackages(); assertEquals(2, packages.size()); Map packagesByName = new HashMap(); for (IPackageCoverage p : packages) { packagesByName.put(p.getName(), p); } IPackageCoverage p1 = packagesByName.get("org/jacoco/examples"); assertNotNull(p1); assertEquals( new HashSet(Arrays.asList("org/jacoco/examples/Sample1", "org/jacoco/examples/Sample2")), getNames(p1.getClasses())); IPackageCoverage p2 = packagesByName.get(""); assertNotNull(p2); assertEquals(Collections.singleton("Sample3"), getNames(p2.getClasses())); } @Test public void testGetNoMatchClasses() { MethodCoverageImpl m = new MethodCoverageImpl("doit", "()V", null); m.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 1); addClass(1, true, "Sample1", null, m); m = new MethodCoverageImpl("doit", "()V", null); m.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 2); addClass(2, true, "Sample2", null, m); m = new MethodCoverageImpl("doit", "()V", null); m.increment(CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, 3); addClass(3, false, "Sample3", null, m); final Set actual = getNames( coverageBuilder.getNoMatchClasses()); final Set expected = new HashSet( Arrays.asList("Sample1", "Sample2")); assertEquals(expected, actual); } private Set getNames(Collection nodes) { Set result = new HashSet(); for (ICoverageNode n : nodes) { result.add(n.getName()); } return result; } private void addClass(long id, boolean nomatch, String name, String source, MethodCoverageImpl... methods) { final ClassCoverageImpl coverage = new ClassCoverageImpl(name, id, nomatch); coverage.setSourceFileName(source); for (MethodCoverageImpl m : methods) { coverage.addMethod(m); } coverageBuilder.visitCoverage(coverage); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/analysis/CoverageNodeImplTest.java000066400000000000000000000122761451257705100312640ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; import static org.jacoco.core.analysis.ICoverageNode.CounterEntity.BRANCH; import static org.jacoco.core.analysis.ICoverageNode.CounterEntity.CLASS; import static org.jacoco.core.analysis.ICoverageNode.CounterEntity.COMPLEXITY; import static org.jacoco.core.analysis.ICoverageNode.CounterEntity.INSTRUCTION; import static org.jacoco.core.analysis.ICoverageNode.CounterEntity.LINE; import static org.jacoco.core.analysis.ICoverageNode.CounterEntity.METHOD; import static org.junit.Assert.assertEquals; import java.util.Arrays; import org.jacoco.core.analysis.ICoverageNode.ElementType; import org.jacoco.core.internal.analysis.CounterImpl; import org.junit.Test; /** * Unit tests for {@link CoverageNodeImpl}. */ public class CoverageNodeImplTest { @Test public void testProperties() { ICoverageNode node = new CoverageNodeImpl(ElementType.GROUP, "sample"); assertEquals(ElementType.GROUP, node.getElementType()); assertEquals("sample", node.getName()); } @Test public void testInit() { ICoverageNode node = new CoverageNodeImpl(ElementType.GROUP, "sample"); assertEquals(CounterImpl.COUNTER_0_0, node.getBranchCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getInstructionCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getLineCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getComplexityCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getMethodCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getClassCounter()); } @Test public void testIncrement() { CoverageNodeImpl parent = new CoverageNodeImpl(ElementType.GROUP, "sample"); ICoverageNode child = new CoverageNodeImpl(ElementType.GROUP, "sample") { { instructionCounter = CounterImpl.getInstance(1, 41); branchCounter = CounterImpl.getInstance(10, 15); lineCounter = CounterImpl.getInstance(5, 3); complexityCounter = CounterImpl.getInstance(4, 2); methodCounter = CounterImpl.getInstance(1, 21); classCounter = CounterImpl.getInstance(1, 11); } }; parent.increment(child); assertEquals(CounterImpl.getInstance(1, 41), parent.getCounter(INSTRUCTION)); assertEquals(CounterImpl.getInstance(1, 41), parent.getInstructionCounter()); assertEquals(CounterImpl.getInstance(10, 15), parent.getCounter(BRANCH)); assertEquals(CounterImpl.getInstance(10, 15), parent.getBranchCounter()); assertEquals(CounterImpl.getInstance(5, 3), parent.getCounter(LINE)); assertEquals(CounterImpl.getInstance(5, 3), parent.getLineCounter()); assertEquals(CounterImpl.getInstance(4, 2), parent.getCounter(COMPLEXITY)); assertEquals(CounterImpl.getInstance(4, 2), parent.getComplexityCounter()); assertEquals(CounterImpl.getInstance(1, 21), parent.getCounter(METHOD)); assertEquals(CounterImpl.getInstance(1, 21), parent.getMethodCounter()); assertEquals(CounterImpl.getInstance(1, 11), parent.getCounter(CLASS)); assertEquals(CounterImpl.getInstance(1, 11), parent.getClassCounter()); } @Test public void testIncrementCollection() { CoverageNodeImpl parent = new CoverageNodeImpl(ElementType.GROUP, "sample"); ICoverageNode child1 = new CoverageNodeImpl(ElementType.GROUP, "sample") { { branchCounter = CounterImpl.getInstance(5, 2); } }; ICoverageNode child2 = new CoverageNodeImpl(ElementType.GROUP, "sample") { { branchCounter = CounterImpl.getInstance(3, 3); } }; parent.increment(Arrays.asList(child1, child2)); assertEquals(CounterImpl.getInstance(8, 5), parent.getBranchCounter()); } @Test public void testGetPlainCopy() { ICoverageNode node = new CoverageNodeImpl(ElementType.CLASS, "Sample") { { classCounter = CounterImpl.getInstance(1, 1); methodCounter = CounterImpl.getInstance(2, 2); branchCounter = CounterImpl.getInstance(3, 3); instructionCounter = CounterImpl.getInstance(4, 4); lineCounter = CounterImpl.getInstance(5, 5); complexityCounter = CounterImpl.getInstance(6, 6); } }; ICoverageNode copy = node.getPlainCopy(); assertEquals(ElementType.CLASS, copy.getElementType()); assertEquals("Sample", copy.getName()); assertEquals(CounterImpl.getInstance(1, 1), copy.getClassCounter()); assertEquals(CounterImpl.getInstance(2, 2), copy.getMethodCounter()); assertEquals(CounterImpl.getInstance(3, 3), copy.getBranchCounter()); assertEquals(CounterImpl.getInstance(4, 4), copy.getInstructionCounter()); assertEquals(CounterImpl.getInstance(5, 5), copy.getLineCounter()); assertEquals(CounterImpl.getInstance(6, 6), copy.getComplexityCounter()); } @Test public void testToString() { CoverageNodeImpl node = new CoverageNodeImpl(ElementType.CLASS, "Test"); assertEquals("Test [CLASS]", node.toString()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/analysis/NodeComparatorTest.java000066400000000000000000000050771451257705100310170ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; import static org.jacoco.core.analysis.ICoverageNode.ElementType.GROUP; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; import java.util.Arrays; import java.util.List; import org.jacoco.core.analysis.ICoverageNode.CounterEntity; import org.jacoco.core.internal.analysis.CounterImpl; import org.junit.Test; /** * Unit test for {@link NodeComparator}. */ public class NodeComparatorTest { @Test public void testSort() { ICoverageNode d1 = new MockNode(18); ICoverageNode d2 = new MockNode(21); ICoverageNode d3 = new MockNode(30); ICoverageNode d4 = new MockNode(60); ICoverageNode d5 = new MockNode(99); final List result = CounterComparator.TOTALITEMS .on(CounterEntity.INSTRUCTION) .sort(Arrays.asList(d3, d5, d1, d4, d2)); assertEquals(Arrays.asList(d1, d2, d3, d4, d5), result); } @Test public void testSecond1() { ICoverageNode d1 = new MockLineData(5, 30); ICoverageNode d2 = new MockLineData(3, 80); final NodeComparator c1 = CounterComparator.TOTALITEMS .on(CounterEntity.INSTRUCTION); final NodeComparator c2 = CounterComparator.TOTALITEMS .on(CounterEntity.LINE); assertTrue(c1.second(c2).compare(d1, d2) > 0); } @Test public void testSecond2() { ICoverageNode d1 = new MockLineData(5, 30); ICoverageNode d2 = new MockLineData(5, 80); final NodeComparator c1 = CounterComparator.TOTALITEMS .on(CounterEntity.INSTRUCTION); final NodeComparator c2 = CounterComparator.TOTALITEMS .on(CounterEntity.LINE); assertTrue(c1.second(c2).compare(d1, d2) < 0); } private static final class MockNode extends CoverageNodeImpl { MockNode(int total) { super(GROUP, "mock"); instructionCounter = CounterImpl.getInstance(total, 0); } } private static final class MockLineData extends CoverageNodeImpl { MockLineData(int totalInstruction, int totalLine) { super(GROUP, "mock"); instructionCounter = CounterImpl.getInstance(totalInstruction, 0); lineCounter = CounterImpl.getInstance(totalLine, 0); } } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/data/000077500000000000000000000000001451257705100234545ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/data/ExecutionDataReaderWriterTest.java000066400000000000000000000234421451257705100322410ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.EOFException; import java.io.IOException; import java.io.OutputStream; import java.util.Arrays; import java.util.Random; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link ExecutionDataReader} and {@link ExecutionDataWriter}. * The tests don't care about the written binary format, they just verify * symmetry. */ public class ExecutionDataReaderWriterTest { protected ByteArrayOutputStream buffer; private ExecutionDataWriter writer; private ExecutionDataStore store; private SessionInfo sessionInfo; private Random random; @Before public void setup() throws IOException { buffer = new ByteArrayOutputStream(); writer = createWriter(buffer); store = new ExecutionDataStore(); random = new Random(5); } @Test public void testEmpty() throws IOException { final ExecutionDataReader reader = createReader(); reader.setSessionInfoVisitor(new ISessionInfoVisitor() { public void visitSessionInfo(final SessionInfo info) { fail("No data expected."); } }); reader.setExecutionDataVisitor(new IExecutionDataVisitor() { public void visitClassExecution(final ExecutionData data) { fail("No data expected."); } }); assertFalse(reader.read()); } @Test public void testFlush() throws IOException { final boolean[] flushCalled = new boolean[] { false }; final OutputStream out = new OutputStream() { @Override public void write(int b) throws IOException { } @Override public void flush() throws IOException { flushCalled[0] = true; } }; new ExecutionDataWriter(out).flush(); assertTrue(flushCalled[0]); } @Test public void testCustomBlocks() throws IOException { buffer.write(0x55); buffer.write(0x66); final ExecutionDataReader reader = new ExecutionDataReader( new ByteArrayInputStream(buffer.toByteArray())) { @Override protected boolean readBlock(byte blocktype) throws IOException { switch (blocktype) { case 0x55: return true; case 0x66: return false; } return super.readBlock(blocktype); } }; assertTrue(reader.read()); } @Test public void testGetFileHeader() { byte[] header = ExecutionDataWriter.getFileHeader(); assertEquals(5, header.length); assertEquals(0x01, 0xFF & header[0]); assertEquals(0xC0, 0xFF & header[1]); assertEquals(0xC0, 0xFF & header[2]); final char version = ExecutionDataWriter.FORMAT_VERSION; assertEquals(version >> 8, 0xFF & header[3]); assertEquals(version & 0xFF, 0xFF & header[4]); } @Test public void testMultipleHeaders() throws IOException { new ExecutionDataWriter(buffer); new ExecutionDataWriter(buffer); new ExecutionDataWriter(buffer); assertFalse(createReader().read()); } @Test(expected = IOException.class) public void testInvalidMagicNumber() throws IOException { buffer = new ByteArrayOutputStream(); buffer.write(ExecutionDataWriter.BLOCK_HEADER); buffer.write(0x12); buffer.write(0x34); createReader().read(); } @Test(expected = IncompatibleExecDataVersionException.class) public void testInvalidVersion() throws IOException { buffer = new ByteArrayOutputStream(); buffer.write(ExecutionDataWriter.BLOCK_HEADER); buffer.write(0xC0); buffer.write(0xC0); final char version = (char) (ExecutionDataWriter.FORMAT_VERSION - 1); buffer.write(version >> 8); buffer.write(version & 0xFF); createReader().read(); } @Test(expected = IOException.class) public void testMissingHeader() throws IOException { buffer.reset(); writer.visitClassExecution( new ExecutionData(Long.MIN_VALUE, "Sample", createData(8))); createReaderWithVisitors().read(); } @Test(expected = IOException.class) public void testUnknownBlock() throws IOException { buffer.write(0xff); createReader().read(); } @Test(expected = EOFException.class) public void testTruncatedFile() throws IOException { writer.visitClassExecution( new ExecutionData(Long.MIN_VALUE, "Sample", createData(8))); final byte[] content = buffer.toByteArray(); buffer.reset(); buffer.write(content, 0, content.length - 1); createReaderWithVisitors().read(); } @Test public void testEmptyFile() throws IOException { buffer.reset(); createReader().read(); } // === Session Info === @Test(expected = IOException.class) public void testNoSessionInfoVisitor() throws IOException { writer.visitSessionInfo(new SessionInfo("x", 0, 1)); createReader().read(); } @Test public void testSessionInfo() throws IOException { writer.visitSessionInfo(new SessionInfo("TestSession", 2837123124567891234L, 3444234223498879234L)); assertFalse(createReaderWithVisitors().read()); assertNotNull(sessionInfo); assertEquals("TestSession", sessionInfo.getId()); assertEquals(2837123124567891234L, sessionInfo.getStartTimeStamp()); assertEquals(3444234223498879234L, sessionInfo.getDumpTimeStamp()); } @Test(expected = RuntimeException.class) public void testSessionInfoIOException() throws IOException { final boolean[] broken = new boolean[1]; final ExecutionDataWriter writer = createWriter(new OutputStream() { @Override public void write(int b) throws IOException { if (broken[0]) { throw new IOException(); } } }); broken[0] = true; writer.visitSessionInfo(new SessionInfo("X", 0, 0)); } // === Execution Data === @Test(expected = IOException.class) public void testNoExecutionDataVisitor() throws IOException { writer.visitClassExecution( new ExecutionData(Long.MIN_VALUE, "Sample", createData(8))); createReader().read(); } @Test public void testMinClassId() throws IOException { final boolean[] data = createData(8); writer.visitClassExecution( new ExecutionData(Long.MIN_VALUE, "Sample", data)); assertFalse(createReaderWithVisitors().read()); assertArrayEquals(data, store.get(Long.MIN_VALUE).getProbes()); } @Test public void testMaxClassId() throws IOException { final boolean[] data = createData(8); writer.visitClassExecution( new ExecutionData(Long.MAX_VALUE, "Sample", data)); assertFalse(createReaderWithVisitors().read()); assertArrayEquals(data, store.get(Long.MAX_VALUE).getProbes()); } @Test public void testEmptyClass() throws IOException { final boolean[] data = createData(0); writer.visitClassExecution(new ExecutionData(3, "Sample", data)); assertFalse(createReaderWithVisitors().read()); assertTrue(store.getContents().isEmpty()); } @Test public void testNoHitClass() throws IOException { final boolean[] data = new boolean[] { false, false, false }; writer.visitClassExecution(new ExecutionData(3, "Sample", data)); assertFalse(createReaderWithVisitors().read()); assertTrue(store.getContents().isEmpty()); } @Test public void testOneClass() throws IOException { final boolean[] data = createData(15); writer.visitClassExecution(new ExecutionData(3, "Sample", data)); assertFalse(createReaderWithVisitors().read()); assertArrayEquals(data, store.get(3).getProbes()); } @Test public void testTwoClasses() throws IOException { final boolean[] data1 = createData(15); final boolean[] data2 = createData(185); writer.visitClassExecution(new ExecutionData(333, "Sample", data1)); writer.visitClassExecution(new ExecutionData(-45, "Sample", data2)); assertFalse(createReaderWithVisitors().read()); assertArrayEquals(data1, store.get(333).getProbes()); assertArrayEquals(data2, store.get(-45).getProbes()); } @Test public void testBigClass() throws IOException { final boolean[] data = createData(3599); writer.visitClassExecution(new ExecutionData(123, "Sample", data)); assertFalse(createReaderWithVisitors().read()); assertArrayEquals(data, store.get(123).getProbes()); } @Test(expected = RuntimeException.class) public void testExecutionDataIOException() throws IOException { final boolean[] broken = new boolean[1]; final ExecutionDataWriter writer = createWriter(new OutputStream() { @Override public void write(int b) throws IOException { if (broken[0]) { throw new IOException(); } } }); broken[0] = true; writer.visitClassExecution( new ExecutionData(3, "Sample", createData(1))); } private ExecutionDataReader createReaderWithVisitors() throws IOException { final ExecutionDataReader reader = createReader(); reader.setExecutionDataVisitor(store); reader.setSessionInfoVisitor(new ISessionInfoVisitor() { public void visitSessionInfo(SessionInfo info) { sessionInfo = info; } }); return reader; } private boolean[] createData(final int probeCount) { final boolean[] data = new boolean[probeCount]; for (int j = 0; j < data.length; j++) { data[j] = random.nextBoolean(); } return data; } private void assertArrayEquals(final boolean[] expected, final boolean[] actual) { assertTrue(Arrays.equals(expected, actual)); } protected ExecutionDataWriter createWriter(OutputStream out) throws IOException { return new ExecutionDataWriter(out); } protected ExecutionDataReader createReader() throws IOException { return new ExecutionDataReader( new ByteArrayInputStream(buffer.toByteArray())); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/data/ExecutionDataStoreTest.java000066400000000000000000000157721451257705100307450ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertSame; import static org.junit.Assert.assertTrue; import java.util.Arrays; import java.util.Collections; import java.util.HashMap; import java.util.HashSet; import java.util.Map; import java.util.Set; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link ExecutionDataStore}. */ public class ExecutionDataStoreTest implements IExecutionDataVisitor { private ExecutionDataStore store; private Map dataOutput; @Before public void setup() { store = new ExecutionDataStore(); dataOutput = new HashMap(); } @Test public void testEmpty() { assertNull(store.get(123)); assertFalse(store.contains("org/jacoco/example/Foo")); store.accept(this); assertEquals(Collections.emptyMap(), dataOutput); } @Test public void testPut() { final boolean[] probes = new boolean[] { false, false, true }; store.put(new ExecutionData(1000, "Sample", probes)); final ExecutionData data = store.get(1000); assertSame(probes, data.getProbes()); assertTrue(store.contains("Sample")); store.accept(this); assertEquals(Collections.singletonMap(Long.valueOf(1000), data), dataOutput); } @Test public void testReentrantAccept() { final boolean[] probes = new boolean[] { false, false, true }; store.put(new ExecutionData(1000, "Sample0", probes)); store.put(new ExecutionData(1001, "Sample1", probes)); store.accept(new IExecutionDataVisitor() { public void visitClassExecution(ExecutionData data) { store.put(new ExecutionData(1002, "Sample2", probes)); ExecutionDataStoreTest.this.visitClassExecution(data); } }); assertEquals(2, dataOutput.size()); } @Test public void testGetContents() { final boolean[] probes = new boolean[] {}; final ExecutionData a = new ExecutionData(1000, "A", probes); store.put(a); final ExecutionData aa = new ExecutionData(1000, "A", probes); store.put(aa); final ExecutionData b = new ExecutionData(1001, "B", probes); store.put(b); final Set actual = new HashSet( store.getContents()); final Set expected = new HashSet( Arrays.asList(a, b)); assertEquals(expected, actual); } @Test public void testGetWithoutCreate() { final ExecutionData data = new ExecutionData(1000, "Sample", new boolean[] {}); store.put(data); assertSame(data, store.get(1000)); } @Test public void testGetWithCreate() { final Long id = Long.valueOf(1000); final ExecutionData data = store.get(id, "Sample", 3); assertEquals(1000, data.getId()); assertEquals("Sample", data.getName()); assertEquals(3, data.getProbes().length); assertFalse(data.getProbes()[0]); assertFalse(data.getProbes()[1]); assertFalse(data.getProbes()[2]); assertSame(data, store.get(id, "Sample", 3)); assertTrue(store.contains("Sample")); } @Test(expected = IllegalStateException.class) public void testGetNegative1() { final boolean[] data = new boolean[] { false, false, true }; store.put(new ExecutionData(1000, "Sample", data)); store.get(Long.valueOf(1000), "Other", 3); } @Test(expected = IllegalStateException.class) public void testGetNegative2() { final boolean[] data = new boolean[] { false, false, true }; store.put(new ExecutionData(1000, "Sample", data)); store.get(Long.valueOf(1000), "Sample", 4); } @Test(expected = IllegalStateException.class) public void testPutNegative() { final boolean[] data = new boolean[0]; store.put(new ExecutionData(1000, "Sample1", data)); store.put(new ExecutionData(1000, "Sample2", data)); } @Test public void testMerge() { final boolean[] data1 = new boolean[] { false, true, false, true }; store.visitClassExecution(new ExecutionData(1000, "Sample", data1)); final boolean[] data2 = new boolean[] { false, true, true, false }; store.visitClassExecution(new ExecutionData(1000, "Sample", data2)); final boolean[] result = store.get(1000).getProbes(); assertFalse(result[0]); assertTrue(result[1]); assertTrue(result[2]); assertTrue(result[3]); } @Test(expected = IllegalStateException.class) public void testMergeNegative() { final boolean[] data1 = new boolean[] { false, false }; store.visitClassExecution(new ExecutionData(1000, "Sample", data1)); final boolean[] data2 = new boolean[] { false, false, false }; store.visitClassExecution(new ExecutionData(1000, "Sample", data2)); } @Test public void testSubtract() { final boolean[] data1 = new boolean[] { false, true, false, true }; store.put(new ExecutionData(1000, "Sample", data1)); final boolean[] data2 = new boolean[] { false, false, true, true }; store.subtract(new ExecutionData(1000, "Sample", data2)); final boolean[] result = store.get(1000).getProbes(); assertFalse(result[0]); assertTrue(result[1]); assertFalse(result[2]); assertFalse(result[3]); } @Test public void testSubtractOtherId() { final boolean[] data1 = new boolean[] { false, true }; store.put(new ExecutionData(1000, "Sample1", data1)); final boolean[] data2 = new boolean[] { true, true }; store.subtract(new ExecutionData(2000, "Sample2", data2)); final boolean[] result = store.get(1000).getProbes(); assertFalse(result[0]); assertTrue(result[1]); assertNull(store.get(2000)); } @Test public void testSubtractStore() { final boolean[] data1 = new boolean[] { false, true, false, true }; store.put(new ExecutionData(1000, "Sample", data1)); final ExecutionDataStore store2 = new ExecutionDataStore(); final boolean[] data2 = new boolean[] { false, false, true, true }; store2.put(new ExecutionData(1000, "Sample", data2)); store.subtract(store2); final boolean[] result = store.get(1000).getProbes(); assertFalse(result[0]); assertTrue(result[1]); assertFalse(result[2]); assertFalse(result[3]); } @Test public void testReset() throws InstantiationException, IllegalAccessException { final boolean[] data1 = new boolean[] { true, true, false }; store.put(new ExecutionData(1000, "Sample", data1)); store.reset(); final boolean[] data2 = store.get(1000).getProbes(); assertNotNull(data2); assertFalse(data2[0]); assertFalse(data2[1]); assertFalse(data2[2]); } // === IExecutionDataOutput === public void visitClassExecution(final ExecutionData data) { dataOutput.put(Long.valueOf(data.getId()), data); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/data/ExecutionDataTest.java000066400000000000000000000104421451257705100277150ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertSame; import static org.junit.Assert.assertTrue; import org.junit.Test; /** * Unit tests for {@link ExecutionData}. */ public class ExecutionDataTest { @Test public void testCreateEmpty() { final ExecutionData e = new ExecutionData(5, "Example", 3); assertEquals(5, e.getId()); assertEquals("Example", e.getName()); assertEquals(3, e.getProbes().length); assertFalse(e.getProbes()[0]); assertFalse(e.getProbes()[1]); assertFalse(e.getProbes()[2]); } @Test public void testGetters() { final boolean[] data = new boolean[0]; final ExecutionData e = new ExecutionData(5, "Example", data); assertEquals(5, e.getId()); assertEquals("Example", e.getName()); assertSame(data, e.getProbes()); } @Test public void testReset() { final ExecutionData e = new ExecutionData(5, "Example", new boolean[] { true, false, true }); e.reset(); assertFalse(e.getProbes()[0]); assertFalse(e.getProbes()[1]); assertFalse(e.getProbes()[2]); } @Test public void testHasHits() { final boolean[] probes = new boolean[] { false, false, false }; final ExecutionData e = new ExecutionData(5, "Example", probes); assertFalse(e.hasHits()); probes[1] = true; assertTrue(e.hasHits()); } @Test public void testHasHits_empty() { final boolean[] probes = new boolean[] {}; final ExecutionData e = new ExecutionData(5, "Example", probes); assertFalse(e.hasHits()); } @Test public void testMerge() { final ExecutionData a = new ExecutionData(5, "Example", new boolean[] { false, true, false, true }); final ExecutionData b = new ExecutionData(5, "Example", new boolean[] { false, false, true, true }); a.merge(b); // b is merged into a: assertFalse(a.getProbes()[0]); assertTrue(a.getProbes()[1]); assertTrue(a.getProbes()[2]); assertTrue(a.getProbes()[3]); // b must not be modified: assertFalse(b.getProbes()[0]); assertFalse(b.getProbes()[1]); assertTrue(b.getProbes()[2]); assertTrue(b.getProbes()[3]); } @Test public void testMergeSubtract() { final ExecutionData a = new ExecutionData(5, "Example", new boolean[] { false, true, false, true }); final ExecutionData b = new ExecutionData(5, "Example", new boolean[] { false, false, true, true }); a.merge(b, false); // b is subtracted from a: assertFalse(a.getProbes()[0]); assertTrue(a.getProbes()[1]); assertFalse(a.getProbes()[2]); assertFalse(a.getProbes()[3]); // b must not be modified: assertFalse(b.getProbes()[0]); assertFalse(b.getProbes()[1]); assertTrue(b.getProbes()[2]); assertTrue(b.getProbes()[3]); } @Test public void testAssertCompatibility() { final ExecutionData a = new ExecutionData(5, "Example", new boolean[] { true }); a.assertCompatibility(5, "Example", 1); } @Test(expected = IllegalStateException.class) public void testAssertCompatibilityNegative1() { final ExecutionData a = new ExecutionData(5, "Example", new boolean[] { true }); a.assertCompatibility(55, "Example", 1); } @Test(expected = IllegalStateException.class) public void testAssertCompatibilityNegative2() { final ExecutionData a = new ExecutionData(5, "Example", new boolean[] { true }); a.assertCompatibility(5, "Exxxample", 1); } @Test(expected = IllegalStateException.class) public void testAssertCompatibilityNegative3() { final ExecutionData a = new ExecutionData(5, "Example", new boolean[] { true }); a.assertCompatibility(5, "Example", 3); } @Test public void testToString() { final ExecutionData a = new ExecutionData(Long.MAX_VALUE, "Example", new boolean[] { true }); assertEquals("ExecutionData[name=Example, id=7fffffffffffffff]", a.toString()); } } IncompatibleExecDataVersionExceptionTest.java000066400000000000000000000027151451257705100343370ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/data/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; import static org.junit.Assert.assertEquals; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link IncompatibleExecDataVersionExceptionTest}. */ public class IncompatibleExecDataVersionExceptionTest { private IncompatibleExecDataVersionException exception; @Before public void setup() { exception = new IncompatibleExecDataVersionException(0x1234); } @Test public void testGetMessage() { String expected = "Cannot read execution data version 0x1234. " + "This version of JaCoCo uses execution data version 0x" + Integer.toHexString(ExecutionDataWriter.FORMAT_VERSION) + "."; assertEquals(expected, exception.getMessage()); } @Test public void testGetActualVersion() { assertEquals(0x1234, exception.getActualVersion()); } @Test public void testGetExpectedVersion() { assertEquals(ExecutionDataWriter.FORMAT_VERSION, exception.getExpectedVersion()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/data/SessionInfoStoreTest.java000066400000000000000000000054741451257705100304450ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.util.List; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link SessionInfoStore}. */ public class SessionInfoStoreTest { private SessionInfoStore store; @Before public void setup() { store = new SessionInfoStore(); } @Test public void testEmpty() { assertEquals(Collections.emptyList(), store.getInfos()); assertTrue(store.isEmpty()); } @Test public void testIsEmpty() { store.visitSessionInfo(new SessionInfo("A", 123, 456)); assertFalse(store.isEmpty()); } @Test public void testGetInfos() { final SessionInfo a = new SessionInfo("A", 12345, 500000); store.visitSessionInfo(a); final SessionInfo b = new SessionInfo("B", 12345, 400000); store.visitSessionInfo(b); final SessionInfo c = new SessionInfo("C", 12345, 600000); store.visitSessionInfo(c); assertEquals(Arrays.asList(b, a, c), store.getInfos()); } @Test public void testGetMergedEmpty() { final SessionInfo info = store.getMerged("MERGE"); assertEquals("MERGE", info.getId()); assertEquals(0, info.getStartTimeStamp()); assertEquals(0, info.getDumpTimeStamp()); } @Test public void testGetMerged() { store.visitSessionInfo(new SessionInfo("A", 23456, 500000)); store.visitSessionInfo(new SessionInfo("B", 12345, 400000)); store.visitSessionInfo(new SessionInfo("C", 34567, 600000)); final SessionInfo info = store.getMerged("MERGE"); assertEquals("MERGE", info.getId()); assertEquals(12345, info.getStartTimeStamp()); assertEquals(600000, info.getDumpTimeStamp()); } @Test public void testAccept() { final SessionInfo a = new SessionInfo("A", 12345, 500000); store.visitSessionInfo(a); final SessionInfo b = new SessionInfo("B", 12345, 400000); store.visitSessionInfo(b); final SessionInfo c = new SessionInfo("C", 12345, 600000); store.visitSessionInfo(c); final List actual = new ArrayList(); store.accept(new ISessionInfoVisitor() { public void visitSessionInfo(SessionInfo info) { actual.add(info); } }); assertEquals(Arrays.asList(b, a, c), actual); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/data/SessionInfoTest.java000066400000000000000000000030071451257705100274160ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; import static org.junit.Assert.assertEquals; import org.junit.Test; /** * Unit tests for {@link SessionInfo}. */ public class SessionInfoTest { @Test(expected = IllegalArgumentException.class) public void testNullId() { new SessionInfo(null, 1, 2); } @Test public void testGetters() { final SessionInfo info = new SessionInfo("id", 1000, 2000); assertEquals("id", info.getId()); assertEquals(1000, info.getStartTimeStamp()); assertEquals(2000, info.getDumpTimeStamp()); } @Test public void testCompare() { assertEquals(0, new SessionInfo("id", 1000, 2000) .compareTo(new SessionInfo("id", 1234, 2000))); assertEquals(-1, new SessionInfo("id", 3333, 1999) .compareTo(new SessionInfo("id", 1234, 2000))); assertEquals(+1, new SessionInfo("id", 1234, 2001) .compareTo(new SessionInfo("id", 2222, 2000))); } @Test public void testToString() { assertEquals("SessionInfo[id]", new SessionInfo("id", 1000, 2000).toString()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/instr/000077500000000000000000000000001451257705100237025ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/instr/ClassFileVersionsTest.java000066400000000000000000000142751451257705100310140ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.instr; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.objectweb.asm.Opcodes.ACC_PUBLIC; import static org.objectweb.asm.Opcodes.ACC_SUPER; import static org.objectweb.asm.Opcodes.ALOAD; import static org.objectweb.asm.Opcodes.F_NEW; import static org.objectweb.asm.Opcodes.IFEQ; import static org.objectweb.asm.Opcodes.ILOAD; import static org.objectweb.asm.Opcodes.INVOKESPECIAL; import static org.objectweb.asm.Opcodes.INVOKEVIRTUAL; import static org.objectweb.asm.Opcodes.POP; import static org.objectweb.asm.Opcodes.RETURN; import static org.objectweb.asm.Opcodes.V10; import static org.objectweb.asm.Opcodes.V11; import static org.objectweb.asm.Opcodes.V12; import static org.objectweb.asm.Opcodes.V13; import static org.objectweb.asm.Opcodes.V14; import static org.objectweb.asm.Opcodes.V15; import static org.objectweb.asm.Opcodes.V16; import static org.objectweb.asm.Opcodes.V1_1; import static org.objectweb.asm.Opcodes.V1_2; import static org.objectweb.asm.Opcodes.V1_3; import static org.objectweb.asm.Opcodes.V1_4; import static org.objectweb.asm.Opcodes.V1_5; import static org.objectweb.asm.Opcodes.V1_6; import static org.objectweb.asm.Opcodes.V1_7; import static org.objectweb.asm.Opcodes.V1_8; import static org.objectweb.asm.Opcodes.V9; import java.io.IOException; import org.jacoco.core.internal.instr.CondyProbeArrayStrategy; import org.jacoco.core.internal.instr.InstrSupport; import org.jacoco.core.runtime.IRuntime; import org.jacoco.core.runtime.SystemPropertiesRuntime; import org.junit.Test; import org.objectweb.asm.ClassVisitor; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.Label; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; /** * Test class inserted stackmap frames for different class file versions. */ public class ClassFileVersionsTest { @Test public void test_1_1() throws IOException { testVersion(V1_1, false); } @Test public void test_1_2() throws IOException { testVersion(V1_2, false); } @Test public void test_1_3() throws IOException { testVersion(V1_3, false); } @Test public void test_1_4() throws IOException { testVersion(V1_4, false); } @Test public void test_1_5() throws IOException { testVersion(V1_5, false); } @Test public void test_1_6() throws IOException { testVersion(V1_6, true); } @Test public void test_1_7() throws IOException { testVersion(V1_7, true); } @Test public void test_1_8() throws IOException { testVersion(V1_8, true); } @Test public void test_9() throws IOException { testVersion(V9, true); } @Test public void test_10() throws IOException { testVersion(V10, true); } @Test public void test_11() throws IOException { testVersion(V11, true); } @Test public void test_12() throws IOException { testVersion(V12, true); } @Test public void test_13() throws IOException { testVersion(V13, true); } @Test public void test_14() throws IOException { testVersion(V14, true); } @Test public void test_15() throws IOException { testVersion(V15, true); } @Test public void test_16() throws IOException { testVersion(V16, true); } private void testVersion(int version, boolean frames) throws IOException { final byte[] original = createClass(version, frames); IRuntime runtime = new SystemPropertiesRuntime(); Instrumenter instrumenter = new Instrumenter(runtime); byte[] instrumented = instrumenter.instrument(original, "TestTarget"); assertFrames(instrumented, frames); } private void assertFrames(byte[] source, final boolean expected) { InstrSupport.classReaderFor(source) .accept(new ClassVisitor(InstrSupport.ASM_API_VERSION) { @Override public MethodVisitor visitMethod(int access, String name, final String desc, String signature, String[] exceptions) { return new MethodVisitor(InstrSupport.ASM_API_VERSION) { boolean frames = false; @Override public void visitFrame(int type, int nLocal, Object[] local, int nStack, Object[] stack) { frames = true; } @Override public void visitEnd() { if (CondyProbeArrayStrategy.B_DESC .equals(desc)) { assertFalse( "CondyProbeArrayStrategy does not need frames", frames); } else { assertEquals(Boolean.valueOf(expected), Boolean.valueOf(frames)); } } }; } }, 0); } /** * Creates a class that requires a frame before the return statement. Also * for this class instrumentation should insert another frame. * *

	 * public class Sample {
	 *   public Sample(boolean b){
	 *     if(b){
	 *       toString();
	 *     }
	 *     return;
	 *   }
	 * }
	 * 
*/ private byte[] createClass(int version, boolean frames) { ClassWriter cw = new ClassWriter(0); MethodVisitor mv; cw.visit(version, ACC_PUBLIC + ACC_SUPER, "org/jacoco/test/Sample", null, "java/lang/Object", null); mv = cw.visitMethod(ACC_PUBLIC, "", "(Z)V", null, null); mv.visitCode(); mv.visitVarInsn(ALOAD, 0); mv.visitMethodInsn(INVOKESPECIAL, "java/lang/Object", "", "()V", false); mv.visitVarInsn(ILOAD, 1); Label l1 = new Label(); mv.visitJumpInsn(IFEQ, l1); mv.visitVarInsn(ALOAD, 0); mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/Object", "toString", "()Ljava/lang/String;", false); mv.visitInsn(POP); mv.visitLabel(l1); if (frames) { mv.visitFrame(F_NEW, 2, new Object[] { "org/jacoco/test/Sample", Opcodes.INTEGER }, 0, new Object[] {}); } mv.visitInsn(RETURN); mv.visitMaxs(1, 2); mv.visitEnd(); cw.visitEnd(); return cw.toByteArray(); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/instr/InstrumenterTest.java000066400000000000000000000367751451257705100301260ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.instr; import static org.junit.Assert.assertArrayEquals; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNull; import static org.junit.Assert.fail; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.ObjectInputStream; import java.io.ObjectOutputStream; import java.io.OutputStream; import java.io.Serializable; import java.util.Arrays; import java.util.zip.CRC32; import java.util.zip.GZIPInputStream; import java.util.zip.GZIPOutputStream; import java.util.zip.ZipEntry; import java.util.zip.ZipInputStream; import java.util.zip.ZipOutputStream; import org.jacoco.core.JaCoCo; import org.jacoco.core.analysis.AnalyzerTest; import org.jacoco.core.internal.Pack200Streams; import org.jacoco.core.internal.data.CRC64; import org.jacoco.core.internal.instr.InstrSupport; import org.jacoco.core.runtime.IExecutionDataAccessorGenerator; import org.jacoco.core.test.TargetLoader; import org.junit.AssumptionViolatedException; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; /** * Unit tests for {@link Instrumenter}. */ public class InstrumenterTest { // no serialVersionUID to enforce calculation @SuppressWarnings("serial") public static class SerializationTarget implements Serializable { private final String text; private final int nr; public SerializationTarget(final String text, final int nr) { this.text = text; this.nr = nr; } @Override public String toString() { return text + nr; } } private static final class AccessorGenerator implements IExecutionDataAccessorGenerator { long classId; public int generateDataAccessor(final long classId, final String classname, final int probeCount, final MethodVisitor mv) { this.classId = classId; InstrSupport.push(mv, probeCount); mv.visitIntInsn(Opcodes.NEWARRAY, Opcodes.T_BOOLEAN); return 1; } } private AccessorGenerator accessorGenerator; private Instrumenter instrumenter; @Before public void setup() throws Exception { accessorGenerator = new AccessorGenerator(); instrumenter = new Instrumenter(accessorGenerator); } @Test public void should_not_modify_class_bytes_to_support_next_version() throws Exception { final byte[] originalBytes = createClass(Opcodes.V21 + 1); final byte[] bytes = new byte[originalBytes.length]; System.arraycopy(originalBytes, 0, bytes, 0, originalBytes.length); final long expectedClassId = CRC64.classId(bytes); instrumenter.instrument(bytes, ""); assertArrayEquals(originalBytes, bytes); assertEquals(expectedClassId, accessorGenerator.classId); } private static byte[] createClass(final int version) { final ClassWriter cw = new ClassWriter(0); cw.visit(version, 0, "Foo", null, "java/lang/Object", null); cw.visitEnd(); return cw.toByteArray(); } /** * @see #instrumentAll_should_throw_exception_for_unsupported_class_file_version() */ @Test public void instrument_should_throw_exception_for_unsupported_class_file_version() { final byte[] bytes = createClass(Opcodes.V21 + 2); try { instrumenter.instrument(bytes, "UnsupportedVersion"); fail("exception expected"); } catch (final IOException e) { assertExceptionMessage("UnsupportedVersion", e); assertEquals("Unsupported class file major version 67", e.getCause().getMessage()); } } @Test public void testInstrumentClass() throws Exception { byte[] bytes = instrumenter.instrument( TargetLoader.getClassDataAsBytes(InstrumenterTest.class), "Test"); TargetLoader loader = new TargetLoader(); Class clazz = loader.add(InstrumenterTest.class, bytes); assertEquals("org.jacoco.core.instr.InstrumenterTest", clazz.getName()); } /** * Triggers exception in {@link Instrumenter#instrument(byte[], String)}. */ @Test public void testInstrumentBrokenClass1() throws IOException { final byte[] brokenclass = TargetLoader .getClassDataAsBytes(AnalyzerTest.class); brokenclass[10] = 0x23; try { instrumenter.instrument(brokenclass, "Broken.class"); fail(); } catch (IOException e) { assertExceptionMessage("Broken.class", e); } } private static class BrokenInputStream extends InputStream { @Override public int read() throws IOException { throw new IOException(); } } /** * Triggers exception in * {@link Instrumenter#instrument(InputStream, String)}. */ @Test public void testInstrumentBrokenStream() { try { instrumenter.instrument(new BrokenInputStream(), "BrokenStream"); fail("exception expected"); } catch (IOException e) { assertExceptionMessage("BrokenStream", e); } } /** * Triggers exception in * {@link Instrumenter#instrument(InputStream, OutputStream, String)}. */ @Test public void testInstrumentBrokenStream2() { try { instrumenter.instrument(new BrokenInputStream(), new ByteArrayOutputStream(), "BrokenStream"); fail("exception expected"); } catch (IOException e) { assertExceptionMessage("BrokenStream", e); } } @Test public void testSerialization() throws Exception { // Create instrumented instance: byte[] bytes = instrumenter.instrument( TargetLoader.getClassData(SerializationTarget.class), "Test"); TargetLoader loader = new TargetLoader(); Object obj1 = loader.add(SerializationTarget.class, bytes) .getConstructor(String.class, Integer.TYPE) .newInstance("Hello", Integer.valueOf(42)); // Serialize instrumented instance: ByteArrayOutputStream buffer = new ByteArrayOutputStream(); new ObjectOutputStream(buffer).writeObject(obj1); // Deserialize with original class definition: Object obj2 = new ObjectInputStream( new ByteArrayInputStream(buffer.toByteArray())).readObject(); assertEquals("Hello42", obj2.toString()); } /** * @see #instrument_should_throw_exception_for_unsupported_class_file_version() */ @Test public void instrumentAll_should_throw_exception_for_unsupported_class_file_version() { final byte[] bytes = createClass(Opcodes.V21 + 2); try { instrumenter.instrumentAll(new ByteArrayInputStream(bytes), new ByteArrayOutputStream(), "UnsupportedVersion"); fail("exception expected"); } catch (final IOException e) { assertExceptionMessage("UnsupportedVersion", e); assertEquals("Unsupported class file major version 67", e.getCause().getMessage()); } } @Test public void testInstrumentAll_Class() throws IOException { InputStream in = TargetLoader.getClassData(getClass()); OutputStream out = new ByteArrayOutputStream(); int count = instrumenter.instrumentAll(in, out, "Test"); assertEquals(1, count); } @Test public void testInstrumentAll_Zip() throws IOException { ByteArrayOutputStream buffer = new ByteArrayOutputStream(); ZipOutputStream zipout = new ZipOutputStream(buffer); // Compressed Entry ZipEntry entry = new ZipEntry("TestCompressed.class"); entry.setMethod(ZipEntry.DEFLATED); zipout.putNextEntry(entry); zipout.write(TargetLoader.getClassDataAsBytes(getClass())); // Uncompressed Entry entry = new ZipEntry("TestUncompressed.class"); entry.setMethod(ZipEntry.STORED); entry.setSize(TargetLoader.getClassDataAsBytes(getClass()).length); CRC32 crc = new CRC32(); crc.update(TargetLoader.getClassDataAsBytes(getClass())); entry.setCrc(crc.getValue()); zipout.putNextEntry(entry); zipout.write(TargetLoader.getClassDataAsBytes(getClass())); zipout.finish(); ByteArrayOutputStream out = new ByteArrayOutputStream(); int count = instrumenter.instrumentAll( new ByteArrayInputStream(buffer.toByteArray()), out, "Test"); assertEquals(2, count); ZipInputStream zipin = new ZipInputStream( new ByteArrayInputStream(out.toByteArray())); entry = zipin.getNextEntry(); assertEquals("TestCompressed.class", entry.getName()); assertEquals(ZipEntry.DEFLATED, entry.getMethod()); entry = zipin.getNextEntry(); assertEquals("TestUncompressed.class", entry.getName()); assertEquals(ZipEntry.STORED, entry.getMethod()); assertNull(zipin.getNextEntry()); } /** * Triggers exception in * {@link org.jacoco.core.internal.ContentTypeDetector#ContentTypeDetector(InputStream)}. */ @Test public void testInstrumentAll_Broken() { try { instrumenter.instrumentAll(new BrokenInputStream(), new ByteArrayOutputStream(), "Broken"); fail("exception expected"); } catch (IOException e) { assertExceptionMessage("Broken", e); } } /** * Triggers exception in * {@link Instrumenter#copy(InputStream, OutputStream)}. */ @Test public void testInstrumentAll_Broken2() { final InputStream inputStream = new InputStream() { private int count; @Override public int read() throws IOException { count++; if (count > 4) { throw new IOException(); } return 0; } }; try { instrumenter.instrumentAll(inputStream, new ByteArrayOutputStream(), "Broken"); } catch (IOException e) { assertExceptionMessage("Broken", e); } } /** * Triggers exception in * {@link Instrumenter#nextEntry(ZipInputStream, String)}. */ @Test public void testInstrumentAll_BrokenZip() { final byte[] buffer = new byte[30]; buffer[0] = 0x50; buffer[1] = 0x4b; buffer[2] = 0x03; buffer[3] = 0x04; Arrays.fill(buffer, 4, buffer.length, (byte) 0x42); try { instrumenter.instrumentAll(new ByteArrayInputStream(buffer), new ByteArrayOutputStream(), "Test.zip"); fail("exception expected"); } catch (IOException e) { assertExceptionMessage("Test.zip", e); } } /** * With JDK <= 6 triggers exception in * {@link Instrumenter#copy(InputStream, OutputStream)}. * * With JDK > 6 triggers exception in * {@link org.jacoco.core.internal.ContentTypeDetector#ContentTypeDetector(InputStream)}. */ @Test public void testInstrumentAll_BrokenZipEntry() throws IOException { ByteArrayOutputStream out = new ByteArrayOutputStream(); ZipOutputStream zip = new ZipOutputStream(out); zip.putNextEntry(new ZipEntry("brokenentry.txt")); out.write(0x23); // Unexpected data here zip.close(); try { instrumenter.instrumentAll( new ByteArrayInputStream(out.toByteArray()), new ByteArrayOutputStream(), "broken.zip"); fail("exception expected"); } catch (IOException e) { assertExceptionMessage("broken.zip@brokenentry.txt", e); } } @Test public void testInstrumentAll_BrokenClassFileInZip() throws IOException { ByteArrayOutputStream buffer = new ByteArrayOutputStream(); ZipOutputStream zipout = new ZipOutputStream(buffer); zipout.putNextEntry(new ZipEntry("Test.class")); final byte[] brokenclass = TargetLoader.getClassDataAsBytes(getClass()); brokenclass[10] = 0x23; zipout.write(brokenclass); zipout.finish(); ByteArrayOutputStream out = new ByteArrayOutputStream(); try { instrumenter.instrumentAll( new ByteArrayInputStream(buffer.toByteArray()), out, "test.zip"); fail(); } catch (IOException e) { assertExceptionMessage("test.zip@Test.class", e); } } /** * Triggers exception in * {@link Instrumenter#instrumentGzip(InputStream, OutputStream, String)}. */ @Test public void testInstrumentAll_BrokenGZ() { final byte[] buffer = new byte[] { 0x1f, (byte) 0x8b, 0x00, 0x00 }; try { instrumenter.instrumentAll(new ByteArrayInputStream(buffer), new ByteArrayOutputStream(), "Test.gz"); fail("exception expected"); } catch (IOException e) { assertExceptionMessage("Test.gz", e); } } @Test public void testInstrumentAll_Pack200() throws IOException { try { Class.forName("java.util.jar.Pack200"); } catch (ClassNotFoundException e) { throw new AssumptionViolatedException( "this test requires JDK with Pack200"); } ByteArrayOutputStream jarbuffer = new ByteArrayOutputStream(); ZipOutputStream zipout = new ZipOutputStream(jarbuffer); zipout.putNextEntry(new ZipEntry("Test.class")); zipout.write(TargetLoader.getClassDataAsBytes(getClass())); zipout.finish(); ByteArrayOutputStream pack200buffer = new ByteArrayOutputStream(); GZIPOutputStream gzipOutput = new GZIPOutputStream(pack200buffer); Pack200Streams.pack(jarbuffer.toByteArray(), gzipOutput); gzipOutput.finish(); ByteArrayOutputStream out = new ByteArrayOutputStream(); int count = instrumenter.instrumentAll( new ByteArrayInputStream(pack200buffer.toByteArray()), out, "Test"); assertEquals(1, count); ZipInputStream zipin = new ZipInputStream( Pack200Streams.unpack(new GZIPInputStream( new ByteArrayInputStream(out.toByteArray())))); assertEquals("Test.class", zipin.getNextEntry().getName()); assertNull(zipin.getNextEntry()); } /** * Triggers exception in * {@link Instrumenter#instrumentPack200(InputStream, OutputStream, String)}. */ @Test public void testInstrumentAll_BrokenPack200() { final byte[] buffer = new byte[] { (byte) 0xca, (byte) 0xfe, (byte) 0xd0, 0x0d }; try { instrumenter.instrumentAll(new ByteArrayInputStream(buffer), new ByteArrayOutputStream(), "Test.pack200"); } catch (IOException e) { assertExceptionMessage("Test.pack200", e); } } @Test public void testInstrumentAll_Other() throws IOException { InputStream in = new ByteArrayInputStream("text".getBytes()); ByteArrayOutputStream out = new ByteArrayOutputStream(); int count = instrumenter.instrumentAll(in, out, "Test"); assertEquals(0, count); assertEquals("text", new String(out.toByteArray())); } @Test public void testInstrumentAll_RemoveSignatures() throws IOException { ByteArrayOutputStream buffer = new ByteArrayOutputStream(); ZipOutputStream zipout = new ZipOutputStream(buffer); zipout.putNextEntry(new ZipEntry("META-INF/MANIFEST.MF")); zipout.putNextEntry(new ZipEntry("META-INF/ALIAS.SF")); zipout.finish(); ByteArrayOutputStream out = new ByteArrayOutputStream(); int count = instrumenter.instrumentAll( new ByteArrayInputStream(buffer.toByteArray()), out, "Test"); assertEquals(0, count); ZipInputStream zipin = new ZipInputStream( new ByteArrayInputStream(out.toByteArray())); assertEquals("META-INF/MANIFEST.MF", zipin.getNextEntry().getName()); assertNull(zipin.getNextEntry()); } @Test public void testInstrumentAll_KeepSignatures() throws IOException { ByteArrayOutputStream buffer = new ByteArrayOutputStream(); ZipOutputStream zipout = new ZipOutputStream(buffer); zipout.putNextEntry(new ZipEntry("META-INF/ALIAS.SF")); zipout.finish(); ByteArrayOutputStream out = new ByteArrayOutputStream(); instrumenter.setRemoveSignatures(false); int count = instrumenter.instrumentAll( new ByteArrayInputStream(buffer.toByteArray()), out, "Test"); assertEquals(0, count); ZipInputStream zipin = new ZipInputStream( new ByteArrayInputStream(out.toByteArray())); assertEquals("META-INF/ALIAS.SF", zipin.getNextEntry().getName()); assertNull(zipin.getNextEntry()); } private void assertExceptionMessage(String name, Exception ex) { String expected = "Error while instrumenting " + name + " with JaCoCo " + JaCoCo.VERSION + "/" + JaCoCo.COMMITID_SHORT + "."; assertEquals(expected, ex.getMessage()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/instr/MethodRecorder.java000066400000000000000000000032211451257705100274510ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.instr; import java.io.PrintWriter; import java.io.StringWriter; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.util.Printer; import org.objectweb.asm.util.Textifier; import org.objectweb.asm.util.TraceMethodVisitor; /** * Recorder of method events for test verification. */ public class MethodRecorder { private final Printer printer; private final MethodVisitor visitor; public MethodRecorder() { printer = new Textifier(); visitor = new TraceMethodVisitor(printer); } public Printer getPrinter() { return printer; } public MethodVisitor getVisitor() { return visitor; } @Override public boolean equals(Object obj) { if (!(obj instanceof MethodRecorder)) { return false; } MethodRecorder that = (MethodRecorder) obj; return printer.getText().equals(that.printer.getText()); } @Override public int hashCode() { return printer.getText().hashCode(); } @Override public String toString() { StringWriter buffer = new StringWriter(); PrintWriter writer = new PrintWriter(buffer); printer.print(writer); writer.flush(); return buffer.toString(); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/instr/ResizeInstructionsTest.java000066400000000000000000000120661451257705100313000ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.instr; import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertSame; import static org.junit.Assert.assertTrue; import org.jacoco.core.internal.instr.InstrSupport; import org.jacoco.core.runtime.IRuntime; import org.jacoco.core.runtime.RuntimeData; import org.jacoco.core.runtime.SystemPropertiesRuntime; import org.jacoco.core.test.TargetLoader; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.ClassReader; import org.objectweb.asm.ClassVisitor; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.Label; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; public class ResizeInstructionsTest { private IRuntime runtime; private Instrumenter instrumenter; private boolean computedCommonSuperClass; @Before public void setup() throws Exception { runtime = new SystemPropertiesRuntime(); instrumenter = new Instrumenter(runtime); runtime.startup(new RuntimeData()); computedCommonSuperClass = false; } @After public void teardown() { runtime.shutdown(); } private class Inner { } /** * Test of ASM bug * #317792. */ @Test public void should_not_loose_InnerClasses_attribute() throws Exception { byte[] source = TargetLoader.getClassDataAsBytes(Inner.class); final ClassReader cr = InstrSupport.classReaderFor(source); final ClassWriter cw = new ClassWriter(0); cr.accept(new ClassVisitor(InstrSupport.ASM_API_VERSION, cw) { @Override public void visitEnd() { final MethodVisitor mv = cv.visitMethod(0, "m", "()V", null, null); mv.visitCode(); addCauseOfResizeInstructions(mv); mv.visitInsn(Opcodes.NOP); mv.visitMaxs(2, 1); mv.visitEnd(); super.visitEnd(); } }, 0); source = cw.toByteArray(); final byte[] bytes = instrumenter.instrument(source, ""); final TargetLoader targetLoader = new TargetLoader(); final Class outer = targetLoader.add(ResizeInstructionsTest.class, TargetLoader.getClassDataAsBytes(ResizeInstructionsTest.class)); final Class inner = targetLoader.add(Inner.class, bytes); assertSame(outer, inner.getEnclosingClass()); assertNotNull(inner.getEnclosingClass()); assertSame(outer, inner.getDeclaringClass()); assertNotNull(inner.getDeclaringClass()); } /** * Test of ASM bug * #317630 that * caused {@code java.lang.ClassNotFoundException}. */ @Test public void should_not_require_computation_of_common_superclass() throws Exception { final String className = "Example"; final ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_FRAMES) { @Override protected String getCommonSuperClass(final String type1, final String type2) { computedCommonSuperClass |= className.equals(type1) || className.equals(type2); return "java/lang/Object"; } }; cw.visit(Opcodes.V1_5, Opcodes.ACC_PUBLIC, className, null, "java/lang/Object", null); final MethodVisitor mv = cw.visitMethod(Opcodes.ACC_PUBLIC, "m", "()V", null, null); mv.visitCode(); addCauseOfResizeInstructions(mv); addCauseOfGetCommonSuperClass(mv); mv.visitMaxs(1, 1); mv.visitEnd(); cw.visitEnd(); final byte[] original = cw.toByteArray(); assertTrue(computedCommonSuperClass); new TargetLoader().add(className, original); final byte[] instrumented = instrumenter.instrument(original, className); new TargetLoader().add(className, instrumented); } /** * Adds code that requires * {@link ClassWriter#getCommonSuperClass(String, String)}. * *
	 * Object o = this;
	 * while (true) {
	 * 	o = (Integer) null;
	 * }
	 * 
*/ private static void addCauseOfGetCommonSuperClass(final MethodVisitor mv) { mv.visitVarInsn(Opcodes.ALOAD, 0); mv.visitVarInsn(Opcodes.ASTORE, 1); Label label = new Label(); mv.visitLabel(label); mv.visitInsn(Opcodes.ACONST_NULL); mv.visitTypeInsn(Opcodes.CHECKCAST, "java/lang/Integer"); mv.visitVarInsn(Opcodes.ASTORE, 1); mv.visitJumpInsn(Opcodes.GOTO, label); } /** * Adds code that triggers usage of * {@link org.objectweb.asm.MethodWriter#COMPUTE_INSERTED_FRAMES} during * instrumentation. */ private static void addCauseOfResizeInstructions(final MethodVisitor mv) { mv.visitInsn(Opcodes.ICONST_0); mv.visitInsn(Opcodes.ICONST_1); final Label target = new Label(); mv.visitJumpInsn(Opcodes.IFLE, target); for (int i = 0; i < Short.MAX_VALUE; i++) { mv.visitInsn(Opcodes.NOP); } mv.visitLabel(target); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/000077500000000000000000000000001451257705100243575ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/ContentTypeDetectorTest.java000066400000000000000000000206551451257705100320400ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal; import static org.junit.Assert.assertEquals; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.util.zip.GZIPOutputStream; import java.util.zip.ZipEntry; import java.util.zip.ZipOutputStream; import org.jacoco.core.test.TargetLoader; import org.junit.AssumptionViolatedException; import org.junit.Test; /** * Unit tests for {@link ContentTypeDetector}. */ public class ContentTypeDetectorTest { private byte[] data; private ContentTypeDetector detector; @Test public void testEmptyStream() throws IOException { initData(); assertEquals(ContentTypeDetector.UNKNOWN, detector.getType()); assertContent(); } @Test public void testClassFile() throws IOException { initData(TargetLoader .getClassDataAsBytes(ContentTypeDetectorTest.class)); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void testClassFile11() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x03, 0x00, 0x2D); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void testClassFile12() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x2E); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void testClassFile13() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x2F); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void testClassFile14() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x30); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void testClassFile15() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x31); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void testClassFile16() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x32); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void testClassFile17() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x33); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void testClassFile18() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x34); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void testClassFile19() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x35); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void should_detect_java_10() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x36); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void should_detect_java_11() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x37); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void should_detect_java_11_with_preview_features() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0xFF, 0xFF, 0x00, 0x37); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void should_detect_java_12() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x38); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void should_detect_java_12_with_preview_features() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0xFF, 0xFF, 0x00, 0x38); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void should_detect_java_13() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x39); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void should_detect_java_13_with_preview_features() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0xFF, 0xFF, 0x00, 0x39); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void should_detect_java_14() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x3A); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void should_detect_java_14_with_preview_features() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0xFF, 0xFF, 0x00, 0x3A); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void should_detect_java_42() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x56); assertEquals(ContentTypeDetector.CLASSFILE, detector.getType()); assertContent(); } @Test public void should_not_detect_MachO_fat_binary_with_44_architectures() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x2C); assertEquals(ContentTypeDetector.UNKNOWN, detector.getType()); assertContent(); } @Test public void testMachObjectFile() throws IOException { initData(0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x02); assertEquals(ContentTypeDetector.UNKNOWN, detector.getType()); assertContent(); } @Test public void testZipFile() throws IOException { final ByteArrayOutputStream buffer = new ByteArrayOutputStream(); final ZipOutputStream zip = new ZipOutputStream(buffer); zip.putNextEntry(new ZipEntry("hello.txt")); zip.write("Hello Zip!".getBytes()); zip.close(); initData(buffer.toByteArray()); assertEquals(ContentTypeDetector.ZIPFILE, detector.getType()); assertContent(); } @Test public void testPack200File() throws IOException { try { Class.forName("java.util.jar.Pack200"); } catch (ClassNotFoundException e) { throw new AssumptionViolatedException( "this test requires JDK with Pack200"); } final ByteArrayOutputStream zipbuffer = new ByteArrayOutputStream(); final ZipOutputStream zip = new ZipOutputStream(zipbuffer); zip.putNextEntry(new ZipEntry("hello.txt")); zip.write("Hello Zip!".getBytes()); zip.close(); final ByteArrayOutputStream pack200buffer = new ByteArrayOutputStream(); Pack200Streams.pack(zipbuffer.toByteArray(), pack200buffer); initData(pack200buffer.toByteArray()); assertEquals(ContentTypeDetector.PACK200FILE, detector.getType()); assertContent(); } @Test public void testGZipFile() throws IOException { final ByteArrayOutputStream buffer = new ByteArrayOutputStream(); final OutputStream gz = new GZIPOutputStream(buffer); gz.write("Hello gz!".getBytes()); gz.close(); initData(buffer.toByteArray()); assertEquals(ContentTypeDetector.GZFILE, detector.getType()); assertContent(); } @Test public void testStreamWithoutMarkSupport() throws IOException { initData(0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07); detector = new ContentTypeDetector(new ByteArrayInputStream(data) { @Override public void mark(int readlimit) { } @Override public void reset() { } @Override public boolean markSupported() { return false; } }); assertContent(); } private void initData(byte[] bytes) throws IOException { this.data = bytes; this.detector = new ContentTypeDetector(new ByteArrayInputStream(data)); } private void initData(final int... bytes) throws IOException { byte[] data = new byte[bytes.length]; for (int i = 0; i < bytes.length; i++) { data[i] = (byte) bytes[i]; } initData(data); } private void assertContent() throws IOException { final InputStream actual = detector.getInputStream(); for (int b : data) { assertEquals(b, (byte) actual.read()); } assertEquals(-1, actual.read()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/Pack200StreamsTest.java000066400000000000000000000151141451257705100305230ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.FilterInputStream; import java.io.FilterOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.util.jar.JarInputStream; import java.util.jar.JarOutputStream; import java.util.zip.ZipEntry; import java.util.zip.ZipInputStream; import java.util.zip.ZipOutputStream; import org.jacoco.core.test.TargetLoader; import org.junit.AssumptionViolatedException; import org.junit.Test; /** * Unit tests for {@link Pack200Streams}. */ public class Pack200StreamsTest { @Test public void pack_should_pack() throws Exception { try { Class.forName("java.util.jar.Pack200"); } catch (ClassNotFoundException e) { throw new AssumptionViolatedException( "this test requires JDK with Pack200"); } ByteArrayOutputStream jarbuffer = new ByteArrayOutputStream(); ZipOutputStream zipout = new ZipOutputStream(jarbuffer); zipout.putNextEntry(new ZipEntry("Test.class")); zipout.write(TargetLoader.getClassDataAsBytes(getClass())); zipout.finish(); ByteArrayOutputStream pack200buffer = new ByteArrayOutputStream(); Pack200Streams.pack(jarbuffer.toByteArray(), new NoCloseOutputStream(pack200buffer)); jarbuffer.reset(); final Object unpacker = Class.forName("java.util.jar.Pack200") .getMethod("newUnpacker").invoke(null); Class.forName("java.util.jar.Pack200$Unpacker") .getMethod("unpack", InputStream.class, JarOutputStream.class) .invoke(unpacker, new ByteArrayInputStream(pack200buffer.toByteArray()), new JarOutputStream(jarbuffer)); ZipInputStream zipin = new ZipInputStream( new ByteArrayInputStream(jarbuffer.toByteArray())); assertEquals("Test.class", zipin.getNextEntry().getName()); assertNull(zipin.getNextEntry()); } @Test public void pack_should_throw_IOException_when_can_not_write_to_OutputStream() { try { Class.forName("java.util.jar.Pack200"); } catch (ClassNotFoundException e) { throw new AssumptionViolatedException( "this test requires JDK with Pack200"); } final OutputStream outputStream = new BrokenOutputStream(); try { Pack200Streams.pack(new byte[0], outputStream); fail("expected exception"); } catch (IOException e) { assertTrue(e.getCause() instanceof IOException); assertEquals("fake broken output stream", e.getCause().getMessage()); } } @Test public void pack_should_throw_IOException_when_Pack200_not_available_in_JDK() { try { Class.forName("java.util.jar.Pack200"); throw new AssumptionViolatedException( "this test requires JDK without Pack200"); } catch (ClassNotFoundException ignore) { } try { Pack200Streams.pack(new byte[0], new ByteArrayOutputStream()); fail("expected exception"); } catch (IOException e) { assertNull(e.getMessage()); assertTrue(e.getCause() instanceof ClassNotFoundException); } } @Test public void unpack_should_unpack() throws Exception { try { Class.forName("java.util.jar.Pack200"); } catch (ClassNotFoundException e) { throw new AssumptionViolatedException( "this test requires JDK with Pack200"); } ByteArrayOutputStream jarbuffer = new ByteArrayOutputStream(); ZipOutputStream zipout = new ZipOutputStream(jarbuffer); zipout.putNextEntry(new ZipEntry("Test.class")); zipout.write(TargetLoader.getClassDataAsBytes(getClass())); zipout.finish(); ByteArrayOutputStream pack200buffer = new ByteArrayOutputStream(); final Object packer = Class.forName("java.util.jar.Pack200") .getMethod("newPacker").invoke(null); Class.forName("java.util.jar.Pack200$Packer") .getMethod("pack", JarInputStream.class, OutputStream.class) .invoke(packer, new JarInputStream( new ByteArrayInputStream(jarbuffer.toByteArray())), pack200buffer); InputStream result = Pack200Streams.unpack(new NoCloseInputStream( new ByteArrayInputStream(pack200buffer.toByteArray()))); ZipInputStream zipin = new ZipInputStream(result); assertEquals("Test.class", zipin.getNextEntry().getName()); assertNull(zipin.getNextEntry()); } @Test public void unpack_should_throw_IOException_when_can_not_read_from_InputStream() { try { Class.forName("java.util.jar.Pack200"); } catch (ClassNotFoundException e) { throw new AssumptionViolatedException( "this test requires JDK with Pack200"); } final InputStream inputStream = new BrokenInputStream(); try { Pack200Streams.unpack(inputStream); fail("expected exception"); } catch (IOException e) { assertTrue(e.getCause() instanceof IOException); assertEquals("fake broken input stream", e.getCause().getMessage()); } } @Test public void unpack_should_throw_IOException_when_Pack200_not_available_in_JDK() { try { Class.forName("java.util.jar.Pack200"); throw new AssumptionViolatedException( "this test requires JDK without Pack200"); } catch (ClassNotFoundException ignore) { } try { Pack200Streams.unpack(new ByteArrayInputStream(new byte[0])); fail("expected exception"); } catch (IOException e) { assertNull(e.getMessage()); assertTrue(e.getCause() instanceof ClassNotFoundException); } } static class NoCloseInputStream extends FilterInputStream { public NoCloseInputStream(InputStream in) { super(in); } @Override public void close() throws IOException { fail(); } } static class NoCloseOutputStream extends FilterOutputStream { public NoCloseOutputStream(OutputStream out) { super(out); } @Override public void close() throws IOException { fail(); } } private static class BrokenInputStream extends InputStream { @Override public int read() throws IOException { throw new IOException("fake broken input stream"); } } private static class BrokenOutputStream extends OutputStream { @Override public void write(int b) throws IOException { throw new IOException("fake broken output stream"); } } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/000077500000000000000000000000001451257705100262025ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/BundleCoverageImplTest.java000066400000000000000000000106211451257705100334140ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertTrue; import java.util.Arrays; import java.util.Collection; import java.util.Collections; import org.jacoco.core.analysis.IClassCoverage; import org.jacoco.core.analysis.ICoverageNode; import org.jacoco.core.analysis.IPackageCoverage; import org.jacoco.core.analysis.ISourceFileCoverage; import org.junit.Test; /** * Unit tests for {@link BundleCoverageImpl}. */ public class BundleCoverageImplTest { @Test public void testProperties() { Collection classes = Collections.emptySet(); Collection sourcefiles = Collections.emptySet(); Collection packages = Collections .singleton((IPackageCoverage) new PackageCoverageImpl("p1", classes, sourcefiles)); BundleCoverageImpl bundle = new BundleCoverageImpl("testbundle", packages); assertEquals(ICoverageNode.ElementType.BUNDLE, bundle.getElementType()); assertEquals("testbundle", bundle.getName()); assertEquals(packages, bundle.getPackages()); } @Test public void testCounters() { Collection classes = Collections.emptySet(); Collection sourcefiles = Collections.emptySet(); final IPackageCoverage p1 = new PackageCoverageImpl("p1", classes, sourcefiles) { { classCounter = CounterImpl.getInstance(1, 0); methodCounter = CounterImpl.getInstance(2, 0); branchCounter = CounterImpl.getInstance(3, 0); instructionCounter = CounterImpl.getInstance(4, 0); lineCounter = CounterImpl.getInstance(5, 0); } }; final IPackageCoverage p2 = new PackageCoverageImpl("p1", classes, sourcefiles) { { classCounter = CounterImpl.getInstance(1, 0); methodCounter = CounterImpl.getInstance(2, 0); branchCounter = CounterImpl.getInstance(3, 0); instructionCounter = CounterImpl.getInstance(4, 0); lineCounter = CounterImpl.getInstance(5, 0); } }; BundleCoverageImpl bundle = new BundleCoverageImpl("testbundle", Arrays.asList(p1, p2)); assertEquals(CounterImpl.getInstance(2, 0), bundle.getClassCounter()); assertEquals(CounterImpl.getInstance(4, 0), bundle.getMethodCounter()); assertEquals(CounterImpl.getInstance(6, 0), bundle.getBranchCounter()); assertEquals(CounterImpl.getInstance(8, 0), bundle.getInstructionCounter()); assertEquals(CounterImpl.getInstance(10, 0), bundle.getLineCounter()); } @Test public void testGroupByPackage() { ClassCoverageImpl ca = new ClassCoverageImpl("p1/A", 1, false); ca.setSourceFileName("A.java"); ClassCoverageImpl cb = new ClassCoverageImpl("p2/B", 2, false); cb.setSourceFileName("B.java"); ISourceFileCoverage sb = new SourceFileCoverageImpl("B.java", "p2"); ISourceFileCoverage sc = new SourceFileCoverageImpl("C.java", "p3"); BundleCoverageImpl bundle = new BundleCoverageImpl("bundle", Arrays.asList((IClassCoverage) ca, (IClassCoverage) cb), Arrays.asList(sb, sc)); Collection packages = bundle.getPackages(); assertEquals(3, packages.size(), 0.0); IPackageCoverage p1 = findPackage("p1", packages); assertNotNull(p1); assertEquals(Collections.singletonList(ca), p1.getClasses()); assertTrue(p1.getSourceFiles().isEmpty()); IPackageCoverage p2 = findPackage("p2", packages); assertNotNull(p2); assertEquals(Collections.singletonList(cb), p2.getClasses()); assertEquals(Collections.singletonList(sb), p2.getSourceFiles()); IPackageCoverage p3 = findPackage("p3", packages); assertNotNull(p3); assertTrue(p3.getClasses().isEmpty()); assertEquals(Collections.singletonList(sc), p3.getSourceFiles()); } private IPackageCoverage findPackage(String name, Collection packages) { for (IPackageCoverage p : packages) { if (name.equals(p.getName())) { return p; } } return null; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/ClassAnalyzerTest.java000066400000000000000000000042241451257705100324620ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; import org.jacoco.core.internal.flow.MethodProbesVisitor; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.Attribute; import org.objectweb.asm.Opcodes; /** * Unit tests for {@link ClassAnalyzer}. */ public class ClassAnalyzerTest { private ClassAnalyzer analyzer; private ClassCoverageImpl coverage; @Before public void setup() { coverage = new ClassCoverageImpl("Foo", 0x0000, false); analyzer = new ClassAnalyzer(coverage, null, new StringPool()); analyzer.visit(Opcodes.V1_5, Opcodes.ACC_PUBLIC, "Foo", null, "java/lang/Object", null); } @Test(expected = IllegalStateException.class) public void testAnalyzeInstrumentedClass1() { analyzer.visitField(InstrSupport.DATAFIELD_ACC, InstrSupport.DATAFIELD_NAME, InstrSupport.DATAFIELD_DESC, null, null); } @Test(expected = IllegalStateException.class) public void testAnalyzeInstrumentedClass2() { analyzer.visitMethod(InstrSupport.INITMETHOD_ACC, InstrSupport.INITMETHOD_NAME, InstrSupport.INITMETHOD_DESC, null, null); } @Test public void testMethodFilter_Empty() { final MethodProbesVisitor mv = analyzer.visitMethod(0, "foo", "()V", null, null); mv.visitEnd(); assertEquals(0, coverage.getMethods().size()); } @Test public void should_collect_attributes() { assertTrue(analyzer.getClassAttributes().isEmpty()); analyzer.visitAttribute(new Attribute("foo") { }); assertTrue(analyzer.getClassAttributes().contains("foo")); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/ClassCoverageImplTest.java000066400000000000000000000072461451257705100332610ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.junit.Assert.assertArrayEquals; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import java.util.Collections; import org.jacoco.core.analysis.ICoverageNode; import org.jacoco.core.analysis.ISourceNode; import org.junit.Before; import org.junit.Test; /** * Unit test for {@link ClassCoverageImpl}. */ public class ClassCoverageImplTest { private ClassCoverageImpl node; @Before public void setup() { node = new ClassCoverageImpl("Sample", 12345, false); } @Test public void testDefaults() { assertEquals(ICoverageNode.ElementType.CLASS, node.getElementType()); assertEquals("Sample", node.getName()); assertEquals(12345, node.getId()); assertFalse(node.isNoMatch()); assertEquals(Collections.emptyList(), node.getMethods()); } @Test public void testSignature() { node.setSignature("LSample;"); assertEquals("LSample;", node.getSignature()); } @Test public void testSuperName() { node.setSuperName("java/lang/Object"); assertEquals("java/lang/Object", node.getSuperName()); } @Test public void testInterfaces() { node.setInterfaces(new String[] { "A", "B" }); assertArrayEquals(new String[] { "A", "B" }, node.getInterfaceNames()); } @Test public void testSourceFileName() { node.setSourceFileName("Sample.java"); assertEquals("Sample.java", node.getSourceFileName()); } @Test public void testNoMatch() { ClassCoverageImpl node = new ClassCoverageImpl("Sample", 12345, true); assertTrue(node.isNoMatch()); } @Test public void testGetPackageName1() { ClassCoverageImpl node = new ClassCoverageImpl("ClassInDefaultPackage", 0, false); assertEquals("", node.getPackageName()); } @Test public void testGetPackageName2() { ClassCoverageImpl data = new ClassCoverageImpl( "org/jacoco/examples/Sample", 0, false); assertEquals("org/jacoco/examples", data.getPackageName()); } @Test public void testEmptyClass() { assertEquals(CounterImpl.COUNTER_0_0, node.getInstructionCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getBranchCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getMethodCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getClassCounter()); } @Test public void testAddMethodMissed() { node.addMethod(createMethod(false)); assertEquals(CounterImpl.COUNTER_1_0, node.getInstructionCounter()); assertEquals(CounterImpl.COUNTER_1_0, node.getMethodCounter()); assertEquals(CounterImpl.COUNTER_1_0, node.getClassCounter()); } @Test public void testAddMethodCovered() { node.addMethod(createMethod(true)); assertEquals(CounterImpl.COUNTER_0_1, node.getInstructionCounter()); assertEquals(CounterImpl.COUNTER_0_1, node.getMethodCounter()); assertEquals(CounterImpl.COUNTER_0_1, node.getClassCounter()); } private MethodCoverageImpl createMethod(boolean covered) { final MethodCoverageImpl m = new MethodCoverageImpl("sample", "()V", null); m.increment(covered ? CounterImpl.COUNTER_0_1 : CounterImpl.COUNTER_1_0, CounterImpl.COUNTER_0_0, ISourceNode.UNKNOWN_LINE); m.incrementMethodCounter(); return m; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/CounterImplTest.java000066400000000000000000000141201451257705100321440ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNotSame; import static org.junit.Assert.assertSame; import org.jacoco.core.analysis.ICounter; import org.jacoco.core.analysis.ICounter.CounterValue; import org.junit.Test; /** * Unit tests for {@link CounterImpl}. */ public class CounterImplTest { @Test public void testGetInstance1() { ICounter c = CounterImpl.getInstance(0, 0); assertEquals(0, c.getTotalCount()); assertEquals(0.0, c.getValue(CounterValue.TOTALCOUNT), 0.0); assertEquals(0, c.getMissedCount()); assertEquals(0.0, c.getValue(CounterValue.MISSEDCOUNT), 0.0); assertEquals(0, c.getCoveredCount()); assertEquals(0.0, c.getValue(CounterValue.COVEREDCOUNT), 0.0); } @Test public void testGetInstance2() { ICounter c = CounterImpl.getInstance(33, 15); assertEquals(48, c.getTotalCount()); assertEquals(48.0, c.getValue(CounterValue.TOTALCOUNT), 0.0); assertEquals(33, c.getMissedCount()); assertEquals(33.0, c.getValue(CounterValue.MISSEDCOUNT), 0.0); assertEquals(15, c.getCoveredCount()); assertEquals(15.0, c.getValue(CounterValue.COVEREDCOUNT), 0.0); } @Test public void testGetInstance3() { ICounter c = CounterImpl.getInstance(15, 12); ICounter copy = CounterImpl.getInstance(c); assertEquals(27, copy.getTotalCount()); assertEquals(27.0, c.getValue(CounterValue.TOTALCOUNT), 0.0); assertEquals(15, copy.getMissedCount()); assertEquals(15.0, c.getValue(CounterValue.MISSEDCOUNT), 0.0); assertEquals(12, copy.getCoveredCount()); assertEquals(12.0, c.getValue(CounterValue.COVEREDCOUNT), 0.0); } @Test public void testFixInstance() { ICounter c1 = CounterImpl.getInstance(30, 30); ICounter c2 = CounterImpl.getInstance(30, 30); assertSame(c1, c2); } @Test public void testVarInstance() { ICounter c1 = CounterImpl.getInstance(31, 30); ICounter c2 = CounterImpl.getInstance(31, 30); assertNotSame(c1, c2); } @Test public void testIncrement1() { CounterImpl c = CounterImpl.getInstance(1, 1); c = c.increment(CounterImpl.getInstance(2, 1)); assertEquals(3, c.getMissedCount()); assertEquals(2, c.getCoveredCount()); } @Test public void testIncrement2() { CounterImpl c = CounterImpl.getInstance(31, 5); c = c.increment(CounterImpl.getInstance(7, 3)); assertEquals(38, c.getMissedCount()); assertEquals(8, c.getCoveredCount()); } @Test public void testGetCoveredRatio1() { ICounter c = CounterImpl.getInstance(30, 10); assertEquals(0.25, c.getCoveredRatio(), 0.0); assertEquals(0.25, c.getValue(CounterValue.COVEREDRATIO), 0.0); } @Test public void testGetCoveredRatio2() { ICounter c = CounterImpl.getInstance(20, 0); assertEquals(0.0, c.getCoveredRatio(), 0.0); assertEquals(0.0, c.getValue(CounterValue.COVEREDRATIO), 0.0); } @Test public void testGetCoveredRatio3() { ICounter c = CounterImpl.getInstance(0, 0); assertEquals(Double.NaN, c.getCoveredRatio(), 0.0); assertEquals(Double.NaN, c.getValue(CounterValue.COVEREDRATIO), 0.0); } @Test public void testGetMissedRatio1() { ICounter c = CounterImpl.getInstance(10, 30); assertEquals(0.25, c.getMissedRatio(), 0.0); assertEquals(0.25, c.getValue(CounterValue.MISSEDRATIO), 0.0); } @Test public void testGetMissedRatio2() { ICounter c = CounterImpl.getInstance(0, 20); assertEquals(0.0, c.getMissedRatio(), 0.0); assertEquals(0.0, c.getValue(CounterValue.MISSEDRATIO), 0.0); } @Test public void testGetMissedRatio3() { ICounter c = CounterImpl.getInstance(0, 0); assertEquals(Double.NaN, c.getMissedRatio(), 0.0); assertEquals(Double.NaN, c.getValue(CounterValue.MISSEDRATIO), 0.0); } @Test public void testGetMissedStatus1() { ICounter c = CounterImpl.getInstance(0, 0); assertEquals(ICounter.EMPTY, c.getStatus()); } @Test public void testGetMissedStatus2() { ICounter c = CounterImpl.getInstance(5, 0); assertEquals(ICounter.NOT_COVERED, c.getStatus()); } @Test public void testGetMissedStatus3() { ICounter c = CounterImpl.getInstance(0, 5); assertEquals(ICounter.FULLY_COVERED, c.getStatus()); } @Test public void testGetMissedStatus4() { ICounter c = CounterImpl.getInstance(2, 3); assertEquals(ICounter.PARTLY_COVERED, c.getStatus()); } @Test public void testEquals1() { ICounter c1 = CounterImpl.getInstance(300, 123); ICounter c2 = CounterImpl.getInstance(300, 123); assertEquals(c1, c2); } @Test public void testEquals2() { ICounter c1 = CounterImpl.getInstance(300, 123); ICounter c2 = CounterImpl.getInstance(400, 123); assertFalse(c1.equals(c2)); } @Test public void testEquals3() { ICounter c1 = CounterImpl.getInstance(300, 123); ICounter c2 = CounterImpl.getInstance(300, 124); assertFalse(c1.equals(c2)); } @Test public void testEquals4() { ICounter c = CounterImpl.getInstance(300, 123); assertFalse(c.equals(new Integer(123))); } @Test public void testHashCode1() { ICounter c1 = CounterImpl.getInstance(300, 123); ICounter c2 = CounterImpl.getInstance(300, 123); assertEquals(c1.hashCode(), c2.hashCode()); } @Test public void testHashCode2() { ICounter c1 = CounterImpl.getInstance(300, 123); ICounter c2 = CounterImpl.getInstance(400, 123); assertFalse(c1.hashCode() == c2.hashCode()); } @Test public void testHashCode3() { ICounter c1 = CounterImpl.getInstance(300, 123); ICounter c2 = CounterImpl.getInstance(300, 124); assertFalse(c1.hashCode() == c2.hashCode()); } @Test public void testToString() { ICounter c = CounterImpl.getInstance(300, 123); assertEquals("Counter[300/123]", c.toString()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/InstructionTest.java000066400000000000000000000114711451257705100322320ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.junit.Assert.assertEquals; import java.util.Arrays; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link Instruction}. */ public class InstructionTest { private Instruction instruction; @Before public void setup() { instruction = new Instruction(123); } @Test public void getLine_should_return_line_number() { assertEquals(123, instruction.getLine()); } @Test public void new_instance_should_have_no_coverage_and_no_branches() { assertEquals(CounterImpl.COUNTER_1_0, instruction.getInstructionCounter()); assertEquals(CounterImpl.COUNTER_0_0, instruction.getBranchCounter()); } @Test public void addBranchWithInstruction_should_not_increment_branches_when_only_one_branch_is_added() { instruction.addBranch(new Instruction(122), 0); assertEquals(CounterImpl.COUNTER_0_0, instruction.getBranchCounter()); } @Test public void addBranchWithInstruction_should_increment_branches_when_two_branches_are_added() { instruction.addBranch(new Instruction(122), 0); instruction.addBranch(new Instruction(123), 1); assertEquals(CounterImpl.getInstance(2, 0), instruction.getBranchCounter()); } @Test public void addBranchWithInstruction_should_propagate_existing_coverage_status() { final Instruction target = new Instruction(122); target.addBranch(true, 0); instruction.addBranch(target, 0); assertEquals(CounterImpl.COUNTER_0_1, instruction.getInstructionCounter()); } @Test public void addBranchWithProbe_should_increment_branches_when_covered() { instruction.addBranch(true, 0); instruction.addBranch(true, 1); assertEquals(CounterImpl.getInstance(0, 1), instruction.getInstructionCounter()); assertEquals(CounterImpl.getInstance(0, 2), instruction.getBranchCounter()); } @Test public void addBranchWithProbe_should_increment_branches_when_not_covered() { instruction.addBranch(false, 0); instruction.addBranch(false, 1); assertEquals(CounterImpl.getInstance(1, 0), instruction.getInstructionCounter()); assertEquals(CounterImpl.getInstance(2, 0), instruction.getBranchCounter()); } @Test public void addBranchWithProbe_should_increment_branches_when_partly_covered() { instruction.addBranch(false, 0); instruction.addBranch(true, 1); assertEquals(CounterImpl.getInstance(0, 1), instruction.getInstructionCounter()); assertEquals(CounterImpl.getInstance(1, 1), instruction.getBranchCounter()); } @Test public void addBranchWithProbe_should_propagate_coverage_status_to_existing_predecessors() { final Instruction i1 = new Instruction(124); final Instruction i2 = new Instruction(125); instruction.addBranch(i1, 3); i1.addBranch(i2, 5); i2.addBranch(true, 8); assertEquals(CounterImpl.COUNTER_0_1, instruction.getInstructionCounter()); } @Test public void addBranch_should_count_large_number_of_branches() { for (int branch = 0; branch < 0x1000; branch++) { instruction.addBranch(true, branch); } assertEquals(CounterImpl.getInstance(0, 0x1000), instruction.getBranchCounter()); } @Test public void addBranch_should_propagate_coverage_status_over_very_long_sequence() { Instruction next = instruction; for (int i = 0; i < 0x10000; i++) { final Instruction insn = new Instruction(i); next.addBranch(insn, 0); next = insn; } next.addBranch(true, 0); assertEquals(CounterImpl.COUNTER_0_1, instruction.getInstructionCounter()); } @Test public void merge_should_calculate_superset_of_covered_branches() { final Instruction i1 = new Instruction(124); i1.addBranch(false, 1); i1.addBranch(false, 2); i1.addBranch(true, 3); i1.addBranch(true, 4); final Instruction i2 = new Instruction(124); i2.addBranch(false, 1); i2.addBranch(true, 2); i2.addBranch(false, 3); i2.addBranch(true, 4); instruction = i1.merge(i2); assertEquals(CounterImpl.getInstance(1, 3), instruction.getBranchCounter()); } @Test public void replaceBranches_should_calculate_coverage_on_new_branches() { Instruction i1 = new Instruction(1); Instruction i2 = new Instruction(2); Instruction i3 = new Instruction(3); i3.addBranch(true, 0); instruction = instruction.replaceBranches(Arrays.asList(i1, i2, i3)); assertEquals(CounterImpl.getInstance(2, 1), instruction.getBranchCounter()); } } InstructionsBuilderTest.java000066400000000000000000000126771451257705100336560ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.junit.Assert.assertEquals; import java.util.Map; import org.jacoco.core.analysis.ISourceNode; import org.jacoco.core.internal.flow.LabelInfo; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.InsnNode; /** * Unit tests for {@link InstructionsBuilder}. */ public class InstructionsBuilderTest { private InstructionsBuilder builder; @Before public void setup() { builder = new InstructionsBuilder(new boolean[] { false, true }); } @Test public void current_line_number_should_be_applied_to_instructions() { InsnNode i1 = new InsnNode(Opcodes.NOP); builder.addInstruction(i1); builder.setCurrentLine(10); InsnNode i2 = new InsnNode(Opcodes.NOP); builder.addInstruction(i2); InsnNode i3 = new InsnNode(Opcodes.NOP); builder.addInstruction(i3); builder.setCurrentLine(20); InsnNode i4 = new InsnNode(Opcodes.NOP); builder.addInstruction(i4); Map map = builder.getInstructions(); assertEquals(ISourceNode.UNKNOWN_LINE, map.get(i1).getLine()); assertEquals(10, map.get(i2).getLine()); assertEquals(10, map.get(i3).getLine()); assertEquals(20, map.get(i4).getLine()); } @Test public void null_probearray_should_not_mark_instruction_as_covered() { builder = new InstructionsBuilder(null); InsnNode i1 = new InsnNode(Opcodes.NOP); builder.addInstruction(i1); builder.addProbe(5, 0); Map map = builder.getInstructions(); assertEquals(CounterImpl.COUNTER_1_0, map.get(i1).getInstructionCounter()); } @Test public void unexecuted_probe_should_not_mark_instruction_as_covered() { InsnNode i1 = new InsnNode(Opcodes.NOP); builder.addInstruction(i1); builder.addProbe(0, 0); Map map = builder.getInstructions(); assertEquals(CounterImpl.COUNTER_1_0, map.get(i1).getInstructionCounter()); } @Test public void executed_probe_should_mark_instruction_as_covered() { InsnNode i1 = new InsnNode(Opcodes.NOP); builder.addInstruction(i1); builder.addProbe(1, 0); Map map = builder.getInstructions(); assertEquals(CounterImpl.COUNTER_0_1, map.get(i1).getInstructionCounter()); } @Test public void subsequent_instructions_should_be_linked_by_default() { InsnNode i1 = new InsnNode(Opcodes.NOP); builder.addInstruction(i1); InsnNode i2 = new InsnNode(Opcodes.NOP); builder.addInstruction(i2); // mark i2 as covered builder.addProbe(1, 0); // coverage should be propagated to i1 Map map = builder.getInstructions(); assertEquals(CounterImpl.COUNTER_0_1, map.get(i1).getInstructionCounter()); } @Test public void subsequent_instructions_should_not_be_linked_when_noSuccessor_was_called() { InsnNode i1 = new InsnNode(Opcodes.NOP); builder.addInstruction(i1); builder.noSuccessor(); InsnNode i2 = new InsnNode(Opcodes.NOP); builder.addInstruction(i2); // mark i2 as covered builder.addProbe(1, 0); // coverage should not be propagated to i1 Map map = builder.getInstructions(); assertEquals(CounterImpl.COUNTER_1_0, map.get(i1).getInstructionCounter()); } @Test public void subsequent_instructions_should_be_linked_after_label_marked_as_successor() { InsnNode i1 = new InsnNode(Opcodes.NOP); builder.addInstruction(i1); Label l = new Label(); LabelInfo.setSuccessor(l); builder.addLabel(l); InsnNode i2 = new InsnNode(Opcodes.NOP); builder.addInstruction(i2); // mark i2 as covered builder.addProbe(1, 0); // coverage should be propagated to i1 Map map = builder.getInstructions(); assertEquals(CounterImpl.COUNTER_0_1, map.get(i1).getInstructionCounter()); } @Test public void subsequent_instructions_should_not_be_linked_after_label_not_marked_as_successor() { InsnNode i1 = new InsnNode(Opcodes.NOP); builder.addInstruction(i1); builder.addLabel(new Label()); InsnNode i2 = new InsnNode(Opcodes.NOP); builder.addInstruction(i2); // mark i2 as covered builder.addProbe(1, 0); // coverage should not be propagated to i1 Map map = builder.getInstructions(); assertEquals(CounterImpl.COUNTER_1_0, map.get(i1).getInstructionCounter()); } @Test public void jumps_should_propagate_coverage_status() { InsnNode i1 = new InsnNode(Opcodes.NOP); builder.addInstruction(i1); Label l2 = new Label(); builder.addJump(l2, 0); builder.addLabel(l2); InsnNode i2 = new InsnNode(Opcodes.NOP); builder.addInstruction(i2); // mark i2 as covered builder.addProbe(1, 0); // coverage should be propagated to i1 Map map = builder.getInstructions(); assertEquals(CounterImpl.COUNTER_0_1, map.get(i1).getInstructionCounter()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/LineImplTest.java000066400000000000000000000121711451257705100314200ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import org.jacoco.core.analysis.ICounter; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link LineImplTest}. */ public class LineImplTest { private LineImpl line; @Before public void setup() { line = LineImpl.EMPTY; } @Test public void testEMPTY() { assertEquals(CounterImpl.COUNTER_0_0, line.getInstructionCounter()); assertEquals(CounterImpl.COUNTER_0_0, line.getBranchCounter()); assertEquals(ICounter.EMPTY, line.getStatus()); } @Test public void testIncrement1() { line = line.increment(CounterImpl.getInstance(1, 2), CounterImpl.getInstance(3, 4)); assertEquals(CounterImpl.getInstance(1, 2), line.getInstructionCounter()); assertEquals(CounterImpl.getInstance(3, 4), line.getBranchCounter()); } @Test public void testIncrement2() { line = line.increment(CounterImpl.getInstance(1, 2), CounterImpl.getInstance(3, 4000)); assertEquals(CounterImpl.getInstance(1, 2), line.getInstructionCounter()); assertEquals(CounterImpl.getInstance(3, 4000), line.getBranchCounter()); } @Test public void testIncrement3() { line = line.increment(CounterImpl.getInstance(1, 2), CounterImpl.getInstance(3000, 4000)); assertEquals(CounterImpl.getInstance(1, 2), line.getInstructionCounter()); assertEquals(CounterImpl.getInstance(3000, 4000), line.getBranchCounter()); } @Test public void testIncrement4() { line = line.increment(CounterImpl.getInstance(1, 2000), CounterImpl.getInstance(3000, 4000)); assertEquals(CounterImpl.getInstance(1, 2000), line.getInstructionCounter()); assertEquals(CounterImpl.getInstance(3000, 4000), line.getBranchCounter()); } @Test public void testIncrement5() { line = line.increment(CounterImpl.getInstance(1000, 2000), CounterImpl.getInstance(3000, 4000)); assertEquals(CounterImpl.getInstance(1000, 2000), line.getInstructionCounter()); assertEquals(CounterImpl.getInstance(3000, 4000), line.getBranchCounter()); } @Test public void testGetStatus1() { line = line.increment(CounterImpl.getInstance(1, 0), CounterImpl.getInstance(0, 0)); assertEquals(ICounter.NOT_COVERED, line.getStatus()); } @Test public void testGetStatus2() { line = line.increment(CounterImpl.getInstance(0, 0), CounterImpl.getInstance(1, 0)); assertEquals(ICounter.NOT_COVERED, line.getStatus()); } @Test public void testGetStatus3() { line = line.increment(CounterImpl.getInstance(0, 1), CounterImpl.getInstance(0, 0)); assertEquals(ICounter.FULLY_COVERED, line.getStatus()); } @Test public void testGetStatus4() { line = line.increment(CounterImpl.getInstance(0, 0), CounterImpl.getInstance(0, 1)); assertEquals(ICounter.FULLY_COVERED, line.getStatus()); } @Test public void testGetStatus5() { line = line.increment(CounterImpl.getInstance(1, 1), CounterImpl.getInstance(0, 0)); assertEquals(ICounter.PARTLY_COVERED, line.getStatus()); } @Test public void testGetStatus6() { line = line.increment(CounterImpl.getInstance(0, 1), CounterImpl.getInstance(1, 1)); assertEquals(ICounter.PARTLY_COVERED, line.getStatus()); } @Test public void testHashCode() { line = line.increment(CounterImpl.getInstance(111, 222), CounterImpl.getInstance(333, 444)); LineImpl line2 = LineImpl.EMPTY; line2 = line2.increment(CounterImpl.getInstance(111, 222), CounterImpl.getInstance(333, 444)); assertEquals(line.hashCode(), line2.hashCode()); } @Test public void testEquals1() { line = line.increment(CounterImpl.getInstance(111, 222), CounterImpl.getInstance(333, 444)); LineImpl line2 = LineImpl.EMPTY; line2 = line2.increment(CounterImpl.getInstance(111, 222), CounterImpl.getInstance(333, 444)); assertEquals(line, line2); } @Test public void testEquals2() { line = line.increment(CounterImpl.getInstance(111, 222), CounterImpl.getInstance(333, 444)); assertFalse(line.equals(new Object())); } @Test public void testEquals3() { line = line.increment(CounterImpl.getInstance(111, 222), CounterImpl.getInstance(333, 444)); LineImpl line2 = LineImpl.EMPTY; line2 = line2.increment(CounterImpl.getInstance(111, 2220), CounterImpl.getInstance(333, 444)); assertFalse(line.equals(line2)); } @Test public void testEquals4() { line = line.increment(CounterImpl.getInstance(111, 222), CounterImpl.getInstance(333, 4440)); LineImpl line2 = LineImpl.EMPTY; line2 = line2.increment(CounterImpl.getInstance(111, 222), CounterImpl.getInstance(333, 444)); assertFalse(line.equals(line2)); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/MethodAnalyzerTest.java000066400000000000000000000644731451257705100326510ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.junit.Assert.assertEquals; import java.util.ArrayList; import java.util.HashSet; import java.util.Set; import org.jacoco.core.analysis.ILine; import org.jacoco.core.analysis.IMethodCoverage; import org.jacoco.core.data.ExecutionDataWriter; import org.jacoco.core.internal.analysis.filter.FilterContextMock; import org.jacoco.core.internal.analysis.filter.Filters; import org.jacoco.core.internal.analysis.filter.IFilter; import org.jacoco.core.internal.analysis.filter.IFilterContext; import org.jacoco.core.internal.analysis.filter.IFilterOutput; import org.jacoco.core.internal.flow.IProbeIdGenerator; import org.jacoco.core.internal.flow.LabelFlowAnalyzer; import org.jacoco.core.internal.flow.MethodProbesAdapter; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.MethodNode; import org.objectweb.asm.tree.TryCatchBlockNode; import org.objectweb.asm.util.CheckMethodAdapter; /** * Unit tests for {@link MethodAnalyzer}. */ public class MethodAnalyzerTest implements IProbeIdGenerator { private int nextProbeId; private boolean[] probes; private MethodNode method; private IMethodCoverage result; @Before public void setup() { nextProbeId = 0; method = new MethodNode(); method.tryCatchBlocks = new ArrayList(); probes = new boolean[32]; } public int nextId() { return nextProbeId++; } // === Scenario: linear Sequence with and without ignore filtering === private void createLinearSequence() { final Label l0 = new Label(); method.visitLabel(l0); method.visitLineNumber(1001, l0); method.visitInsn(Opcodes.NOP); method.visitInsn(Opcodes.NOP); final Label l1 = new Label(); method.visitLabel(l1); method.visitLineNumber(1002, l1); method.visitInsn(Opcodes.RETURN); } @Test public void linear_instruction_sequence_should_create_1_probe() { createLinearSequence(); runMethodAnalzer(); assertEquals(1, nextProbeId); } @Test public void linear_instruction_sequence_should_show_missed_when_no_probe_is_executed() { createLinearSequence(); runMethodAnalzer(); assertLine(1001, 2, 0, 0, 0); assertLine(1002, 1, 0, 0, 0); } @Test public void linear_instruction_sequence_should_show_missed_when_probearray_is_null() { createLinearSequence(); probes = null; runMethodAnalzer(); assertLine(1001, 2, 0, 0, 0); assertLine(1002, 1, 0, 0, 0); } @Test public void linear_instruction_sequence_should_show_covered_when_probe_is_executed() { createLinearSequence(); probes[0] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 0, 0); assertLine(1002, 0, 1, 0, 0); } /** Filters the NOP instructions as ignored */ private static final IFilter NOP_FILTER = new IFilter() { public void filter(final MethodNode methodNode, final IFilterContext context, final IFilterOutput output) { final AbstractInsnNode i1 = methodNode.instructions.get(2); final AbstractInsnNode i2 = methodNode.instructions.get(3); assertEquals(Opcodes.NOP, i1.getOpcode()); assertEquals(Opcodes.NOP, i2.getOpcode()); output.ignore(i1, i2); } }; @Test public void linear_instruction_sequence_should_ignore_instructions_when_filter_is_applied() { createLinearSequence(); probes[0] = true; runMethodAnalzer(NOP_FILTER); assertEquals(1002, result.getFirstLine()); assertEquals(1002, result.getLastLine()); assertLine(1001, 0, 0, 0, 0); assertLine(1002, 0, 1, 0, 0); } // === Scenario: method invocation after zero line number /** * @see org.jacoco.core.internal.flow.LabelFlowAnalyzer#visitLineNumber(int, * Label) * @see org.jacoco.core.internal.instr.ZeroLineNumberTest */ private void createZeroLineNumber() { final Label l0 = new Label(); method.visitLabel(l0); method.visitLineNumber(1001, l0); method.visitInsn(Opcodes.NOP); final Label l1 = new Label(); method.visitLabel(l1); method.visitLineNumber(0, l1); method.visitMethodInsn(Opcodes.INVOKESTATIC, "Foo", "foo", "()V", false); method.visitInsn(Opcodes.NOP); final Label l2 = new Label(); method.visitLabel(l2); method.visitLineNumber(1002, l2); method.visitInsn(Opcodes.RETURN); } @Test public void zero_line_number_should_create_1_probe() { createZeroLineNumber(); runMethodAnalzer(); assertEquals(1, nextProbeId); // workaround for zero line number can be removed if needed // during change of exec file version assertEquals(0x1007, ExecutionDataWriter.FORMAT_VERSION); } @Test public void zero_line_number_should_show_missed_when_no_probes_are_executed() { createZeroLineNumber(); runMethodAnalzer(); assertLine(1001, 1, 0, 0, 0); assertLine(0, 2, 0, 0, 0); assertLine(1002, 1, 0, 0, 0); } @Test public void zero_line_number_should_show_covered_when_probe_is_executed() { createZeroLineNumber(); probes[0] = true; runMethodAnalzer(); assertLine(1001, 0, 1, 0, 0); assertLine(0, 0, 2, 0, 0); assertLine(1002, 0, 1, 0, 0); } // === Scenario: simple if branch === private void createIfBranch() { final Label l0 = new Label(); method.visitLabel(l0); method.visitLineNumber(1001, l0); method.visitVarInsn(Opcodes.ILOAD, 1); Label l1 = new Label(); method.visitJumpInsn(Opcodes.IFEQ, l1); final Label l2 = new Label(); method.visitLabel(l2); method.visitLineNumber(1002, l2); method.visitLdcInsn("a"); method.visitInsn(Opcodes.ARETURN); method.visitLabel(l1); method.visitLineNumber(1003, l1); method.visitLdcInsn("b"); method.visitInsn(Opcodes.ARETURN); } @Test public void if_branch_should_create_2_probes() { createIfBranch(); runMethodAnalzer(); assertEquals(2, nextProbeId); } @Test public void if_branch_should_show_missed_when_no_probes_are_executed() { createIfBranch(); runMethodAnalzer(); assertLine(1001, 2, 0, 2, 0); assertLine(1002, 2, 0, 0, 0); assertLine(1003, 2, 0, 0, 0); } @Test public void if_branch_should_show_partial_branch_coverage_when_probe_for_first_branch_is_executed() { createIfBranch(); probes[0] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 1, 1); assertLine(1002, 0, 2, 0, 0); assertLine(1003, 2, 0, 0, 0); } @Test public void if_branch_should_show_partial_branch_coverage_when_probe_for_second_branch_is_executed() { createIfBranch(); probes[1] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 1, 1); assertLine(1002, 2, 0, 0, 0); assertLine(1003, 0, 2, 0, 0); } @Test public void if_branch_should_show_full_branch_coverage_when_probes_for_both_branches_are_executed() { createIfBranch(); probes[0] = true; probes[1] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 0, 2); assertLine(1002, 0, 2, 0, 0); assertLine(1003, 0, 2, 0, 0); } // === Scenario: branch before unconditional probe === /** * Covers case of * {@link MethodAnalyzer#visitJumpInsnWithProbe(int, Label, int, org.jacoco.core.internal.flow.IFrame)}. */ private void createIfBranchBeforeProbe() { final Label l0 = new Label(); final Label l1 = new Label(); final Label l2 = new Label(); method.visitLabel(l0); method.visitLineNumber(1001, l0); method.visitVarInsn(Opcodes.ILOAD, 1); method.visitJumpInsn(Opcodes.IFNE, l1); method.visitLabel(l2); method.visitLineNumber(1002, l2); method.visitMethodInsn(Opcodes.INVOKESTATIC, "Foo", "foo", "()V", false); method.visitLabel(l1); method.visitLineNumber(1003, l1); method.visitInsn(Opcodes.RETURN); } @Test public void if_branch_before_probes_should_create_4_probes() { createIfBranchBeforeProbe(); runMethodAnalzer(); assertEquals(4, nextProbeId); } @Test public void if_branch_before_probes_should_show_missed_when_no_probes_are_executed() { createIfBranchBeforeProbe(); runMethodAnalzer(); assertLine(1001, 2, 0, 2, 0); assertLine(1002, 1, 0, 0, 0); assertLine(1003, 1, 0, 0, 0); } @Test public void if_branch_before_probes_should_show_partial_branch_coverage_when_probe_for_first_branch_is_executed() { createIfBranchBeforeProbe(); probes[0] = true; probes[3] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 1, 1); assertLine(1002, 1, 0, 0, 0); assertLine(1003, 0, 1, 0, 0); } @Test public void if_branch_before_probes_should_show_partial_branch_coverage_when_probe_for_second_branch_is_executed() { createIfBranchBeforeProbe(); probes[1] = true; probes[2] = true; probes[3] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 1, 1); assertLine(1002, 0, 1, 0, 0); assertLine(1003, 0, 1, 0, 0); } @Test public void if_branch_before_probes_should_show_full_branch_coverage_when_probes_for_both_branches_are_executed() { createIfBranchBeforeProbe(); probes[0] = true; probes[1] = true; probes[2] = true; probes[3] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 0, 2); assertLine(1002, 0, 1, 0, 0); assertLine(1003, 0, 1, 0, 0); } // === Scenario: branch which merges back === private void createIfBranchMerge() { final Label l0 = new Label(); method.visitLabel(l0); method.visitLineNumber(1001, l0); method.visitVarInsn(Opcodes.ILOAD, 1); Label l1 = new Label(); method.visitJumpInsn(Opcodes.IFEQ, l1); final Label l2 = new Label(); method.visitLabel(l2); method.visitLineNumber(1002, l2); method.visitInsn(Opcodes.NOP); method.visitLabel(l1); method.visitLineNumber(1003, l1); method.visitInsn(Opcodes.RETURN); } @Test public void if_branch_merge_should_create_3_probes() { createIfBranchMerge(); runMethodAnalzer(); assertEquals(3, nextProbeId); } @Test public void if_branch_merge_should_show_missed_when_no_probes_are_executed() { createIfBranchMerge(); runMethodAnalzer(); assertLine(1001, 2, 0, 2, 0); assertLine(1002, 1, 0, 0, 0); assertLine(1003, 1, 0, 0, 0); } @Test public void if_branch_merge_should_show_partial_branch_coverage_when_probe_for_first_branch_is_executed() { createIfBranchMerge(); probes[0] = true; probes[2] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 1, 1); assertLine(1002, 1, 0, 0, 0); assertLine(1003, 0, 1, 0, 0); } @Test public void if_branch_merge_should_show_partial_branch_coverage_when_probe_for_second_branch_is_executed() { createIfBranchMerge(); probes[1] = true; probes[2] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 1, 1); assertLine(1002, 0, 1, 0, 0); assertLine(1003, 0, 1, 0, 0); } @Test public void if_branch_merge_should_show_full_branch_coverage_when_probes_for_both_branches_are_executed() { createIfBranchMerge(); probes[0] = true; probes[1] = true; probes[2] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 0, 2); assertLine(1002, 0, 1, 0, 0); assertLine(1003, 0, 1, 0, 0); } // === Scenario: branch which jumps backwards === private void createJumpBackwards() { final Label l0 = new Label(); method.visitLabel(l0); method.visitLineNumber(1001, l0); final Label l1 = new Label(); method.visitJumpInsn(Opcodes.GOTO, l1); final Label l2 = new Label(); method.visitLabel(l2); method.visitLineNumber(1002, l2); method.visitInsn(Opcodes.RETURN); method.visitLabel(l1); method.visitLineNumber(1003, l1); method.visitJumpInsn(Opcodes.GOTO, l2); } @Test public void jump_backwards_should_create_1_probe() { createJumpBackwards(); runMethodAnalzer(); assertEquals(1, nextProbeId); } @Test public void jump_backwards_should_show_missed_when_no_probes_are_executed() { createJumpBackwards(); runMethodAnalzer(); assertLine(1001, 1, 0, 0, 0); assertLine(1002, 1, 0, 0, 0); assertLine(1003, 1, 0, 0, 0); } @Test public void jump_backwards_should_show_covered_when_probe_is_executed() { createJumpBackwards(); probes[0] = true; runMethodAnalzer(); assertLine(1001, 0, 1, 0, 0); assertLine(1002, 0, 1, 0, 0); assertLine(1003, 0, 1, 0, 0); } // === Scenario: jump to first instruction === private void createJumpToFirst() { final Label l1 = new Label(); method.visitLabel(l1); method.visitLineNumber(1001, l1); method.visitVarInsn(Opcodes.ALOAD, 0); method.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Foo", "test", "()Z", false); method.visitJumpInsn(Opcodes.IFEQ, l1); final Label l2 = new Label(); method.visitLabel(l2); method.visitLineNumber(1002, l2); method.visitInsn(Opcodes.RETURN); } @Test public void jump_to_first_instruction_should_create_2_probes() { createJumpToFirst(); runMethodAnalzer(); assertEquals(2, nextProbeId); } @Test public void jump_to_first_instruction_should_show_missed_when_no_probes_are_executed() { createJumpToFirst(); runMethodAnalzer(); assertLine(1001, 3, 0, 2, 0); assertLine(1002, 1, 0, 0, 0); } @Test public void jump_to_first_instruction_should_show_partial_branch_coverage_when_probe_for_first_branch_is_executed() { createJumpToFirst(); probes[0] = true; runMethodAnalzer(); assertLine(1001, 0, 3, 1, 1); assertLine(1002, 1, 0, 0, 0); } @Test public void jump_to_first_instruction_should_show_full_branch_coverage_when_probes_for_both_branches_are_executed() { createJumpToFirst(); probes[0] = true; probes[1] = true; runMethodAnalzer(); assertLine(1001, 0, 3, 0, 2); assertLine(1002, 0, 1, 0, 0); } // === Scenario: table switch with and without replace filtering === private void createTableSwitch() { final Label l0 = new Label(); method.visitLabel(l0); method.visitLineNumber(1001, l0); method.visitVarInsn(Opcodes.ILOAD, 1); Label l1 = new Label(); Label l2 = new Label(); Label l3 = new Label(); method.visitTableSwitchInsn(1, 3, l3, new Label[] { l1, l2, l1 }); method.visitLabel(l1); method.visitLineNumber(1002, l1); method.visitIntInsn(Opcodes.BIPUSH, 11); method.visitVarInsn(Opcodes.ISTORE, 2); final Label l4 = new Label(); method.visitLabel(l4); method.visitLineNumber(1003, l4); Label l5 = new Label(); method.visitJumpInsn(Opcodes.GOTO, l5); method.visitLabel(l2); method.visitLineNumber(1004, l2); method.visitIntInsn(Opcodes.BIPUSH, 22); method.visitVarInsn(Opcodes.ISTORE, 2); final Label l6 = new Label(); method.visitLabel(l6); method.visitLineNumber(1005, l6); method.visitJumpInsn(Opcodes.GOTO, l5); method.visitLabel(l3); method.visitLineNumber(1006, l3); method.visitInsn(Opcodes.ICONST_0); method.visitVarInsn(Opcodes.ISTORE, 2); method.visitLabel(l5); method.visitLineNumber(1007, l5); method.visitVarInsn(Opcodes.ILOAD, 2); method.visitInsn(Opcodes.IRETURN); } @Test public void table_switch_should_create_4_probes() { createTableSwitch(); runMethodAnalzer(); assertEquals(4, nextProbeId); } private static final IFilter SWITCH_FILTER = new IFilter() { public void filter(final MethodNode methodNode, final IFilterContext context, final IFilterOutput output) { final AbstractInsnNode i = methodNode.instructions.get(3); assertEquals(Opcodes.TABLESWITCH, i.getOpcode()); final AbstractInsnNode t1 = methodNode.instructions.get(6); assertEquals(Opcodes.BIPUSH, t1.getOpcode()); final AbstractInsnNode t2 = methodNode.instructions.get(13); assertEquals(Opcodes.BIPUSH, t2.getOpcode()); final Set newTargets = new HashSet(); newTargets.add(t1); newTargets.add(t2); output.replaceBranches(i, newTargets); } }; @Test public void table_switch_with_filter_should_show_2_branches_when_original_replaced() { createTableSwitch(); runMethodAnalzer(SWITCH_FILTER); assertLine(1001, 2, 0, 2, 0); } @Test public void table_switch_with_filter_should_show_full_branch_coverage_when_new_targets_covered() { createTableSwitch(); probes[0] = true; probes[1] = true; runMethodAnalzer(SWITCH_FILTER); assertLine(1001, 0, 2, 0, 2); } @Test public void table_switch_should_show_missed_when_no_probes_are_executed() { createTableSwitch(); runMethodAnalzer(); assertLine(1001, 2, 0, 3, 0); assertLine(1002, 2, 0, 0, 0); assertLine(1003, 1, 0, 0, 0); assertLine(1004, 2, 0, 0, 0); assertLine(1005, 1, 0, 0, 0); assertLine(1006, 2, 0, 0, 0); assertLine(1007, 2, 0, 0, 0); } @Test public void table_switch_should_show_partial_branch_coverage_when_probes_for_first_branch_and_default_are_executed() { createTableSwitch(); probes[0] = true; probes[3] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 2, 1); assertLine(1002, 0, 2, 0, 0); assertLine(1003, 0, 1, 0, 0); assertLine(1004, 2, 0, 0, 0); assertLine(1005, 1, 0, 0, 0); assertLine(1006, 2, 0, 0, 0); assertLine(1007, 0, 2, 0, 0); } @Test public void table_switch_should_show_partial_branch_coverage_when_probes_for_third_branch_and_default_are_executed() { createTableSwitch(); probes[2] = true; probes[3] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 2, 1); assertLine(1002, 2, 0, 0, 0); assertLine(1003, 1, 0, 0, 0); assertLine(1004, 2, 0, 0, 0); assertLine(1005, 1, 0, 0, 0); assertLine(1006, 0, 2, 0, 0); assertLine(1007, 0, 2, 0, 0); } @Test public void table_switch_should_show_full_branch_coverage_when_all_probes_are_executed() { createTableSwitch(); probes[0] = true; probes[1] = true; probes[2] = true; probes[3] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 0, 3); assertLine(1002, 0, 2, 0, 0); assertLine(1003, 0, 1, 0, 0); assertLine(1004, 0, 2, 0, 0); assertLine(1005, 0, 1, 0, 0); assertLine(1006, 0, 2, 0, 0); assertLine(1007, 0, 2, 0, 0); } // === Scenario: table switch with merge === private void createTableSwitchMerge() { final Label l0 = new Label(); method.visitLabel(l0); method.visitLineNumber(1001, l0); method.visitInsn(Opcodes.ICONST_0); method.visitVarInsn(Opcodes.ISTORE, 2); final Label l1 = new Label(); method.visitLabel(l1); method.visitLineNumber(1002, l1); method.visitVarInsn(Opcodes.ILOAD, 1); Label l2 = new Label(); Label l3 = new Label(); Label l4 = new Label(); method.visitTableSwitchInsn(1, 3, l4, new Label[] { l2, l3, l2 }); method.visitLabel(l2); method.visitLineNumber(1003, l2); method.visitIincInsn(2, 1); method.visitLabel(l3); method.visitLineNumber(1004, l3); method.visitIincInsn(2, 1); method.visitLabel(l4); method.visitLineNumber(1005, l4); method.visitVarInsn(Opcodes.ILOAD, 2); method.visitInsn(Opcodes.IRETURN); } @Test public void table_switch_with_merge_should_create_5_probes() { createTableSwitchMerge(); runMethodAnalzer(); assertEquals(5, nextProbeId); } @Test public void table_switch_with_merge_should_show_missed_when_no_probes_are_executed() { createTableSwitchMerge(); runMethodAnalzer(); assertLine(1001, 2, 0, 0, 0); assertLine(1002, 2, 0, 3, 0); assertLine(1003, 1, 0, 0, 0); assertLine(1004, 1, 0, 0, 0); assertLine(1005, 2, 0, 0, 0); } @Test public void table_switch_with_merge_should_show_two_missed_cases_when_probes_for_these_branches_are_not_executed() { createTableSwitchMerge(); probes[0] = true; probes[4] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 0, 0); assertLine(1002, 0, 2, 2, 1); assertLine(1003, 1, 0, 0, 0); assertLine(1004, 1, 0, 0, 0); assertLine(1005, 0, 2, 0, 0); } @Test public void table_switch_with_merge_should_show_one_missed_case_when_probe_for_this_branch_is_not_executed() { createTableSwitchMerge(); probes[1] = true; probes[3] = true; probes[4] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 0, 0); assertLine(1002, 0, 2, 2, 1); assertLine(1003, 1, 0, 0, 0); assertLine(1004, 0, 1, 0, 0); assertLine(1005, 0, 2, 0, 0); } @Test public void table_switch_with_merge_should_show_partial_branch_coverage_when_probe_for_one_branch_is_not_executed() { createTableSwitchMerge(); probes[2] = true; probes[3] = true; probes[4] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 0, 0); assertLine(1002, 0, 2, 2, 1); assertLine(1003, 0, 1, 0, 0); assertLine(1004, 0, 1, 0, 0); assertLine(1005, 0, 2, 0, 0); } @Test public void table_switch_with_merge_should_show_full_branch_coverage_when_all_probes_are_executed() { createTableSwitchMerge(); probes[0] = true; probes[1] = true; probes[2] = true; probes[3] = true; probes[4] = true; runMethodAnalzer(); assertLine(1001, 0, 2, 0, 0); assertLine(1002, 0, 2, 0, 3); assertLine(1003, 0, 1, 0, 0); assertLine(1004, 0, 1, 0, 0); assertLine(1005, 0, 2, 0, 0); } // === Scenario: try/catch block === private void createTryCatchBlock() { Label l1 = new Label(); Label l2 = new Label(); Label l3 = new Label(); Label l4 = new Label(); method.visitTryCatchBlock(l1, l2, l3, "java/lang/Exception"); method.visitLabel(l1); method.visitLineNumber(1001, l1); method.visitVarInsn(Opcodes.ALOAD, 0); method.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "printStackTrace", "()V", false); method.visitLabel(l2); method.visitJumpInsn(Opcodes.GOTO, l4); method.visitLabel(l3); method.visitLineNumber(1002, l3); method.visitVarInsn(Opcodes.ASTORE, 1); method.visitLabel(l4); method.visitLineNumber(1003, l4); method.visitInsn(Opcodes.RETURN); } @Test public void try_catch_should_create_3_probes() { createTryCatchBlock(); runMethodAnalzer(); assertEquals(3, nextProbeId); } @Test public void try_catch_should_show_missed_when_no_probes_are_executed() { createTryCatchBlock(); runMethodAnalzer(); assertLine(1001, 3, 0, 0, 0); assertLine(1002, 1, 0, 0, 0); assertLine(1003, 1, 0, 0, 0); } @Test public void try_catch_should_show_exception_handler_missed_when_probe_is_not_executed() { createTryCatchBlock(); probes[0] = true; probes[2] = true; runMethodAnalzer(); assertLine(1001, 0, 3, 0, 0); assertLine(1002, 1, 0, 0, 0); assertLine(1003, 0, 1, 0, 0); } @Test public void try_catch_should_show_all_covered_when_all_probes_are_executed() { createTryCatchBlock(); probes[0] = true; probes[1] = true; probes[2] = true; runMethodAnalzer(); assertLine(1001, 0, 3, 0, 0); assertLine(1002, 0, 1, 0, 0); assertLine(1003, 0, 1, 0, 0); } // === Scenario: try/finally with and without merge filtering === private void createTryFinally() { final Label l0 = new Label(); final Label l1 = new Label(); final Label l2 = new Label(); final Label l3 = new Label(); method.visitTryCatchBlock(l0, l2, l2, null); method.visitLabel(l0); method.visitLineNumber(1001, l0); method.visitJumpInsn(Opcodes.IFEQ, l1); // probe[0] method.visitInsn(Opcodes.RETURN); method.visitLabel(l1); // probe[1] method.visitInsn(Opcodes.RETURN); method.visitLabel(l2); method.visitJumpInsn(Opcodes.IFEQ, l3); // probe[2] method.visitInsn(Opcodes.RETURN); method.visitLabel(l3); // probe[3] method.visitInsn(Opcodes.RETURN); } @Test public void try_finally_should_create_4_probes() { createTryFinally(); runMethodAnalzer(); assertEquals(4, nextProbeId); } @Test public void try_finally_without_filter_should_show_all_branches() { createTryFinally(); probes[0] = true; probes[3] = true; runMethodAnalzer(); assertLine(1001, 2, 4, 2, 2); } private static final IFilter TRY_FINALLY_FILTER = new IFilter() { public void filter(final MethodNode methodNode, final IFilterContext context, final IFilterOutput output) { final AbstractInsnNode i1 = methodNode.instructions.get(2); final AbstractInsnNode i2 = methodNode.instructions.get(7); assertEquals(Opcodes.IFEQ, i1.getOpcode()); assertEquals(Opcodes.IFEQ, i2.getOpcode()); output.merge(i1, i2); // Merging of already merged instructions won't change result: output.merge(i1, i2); } }; @Test public void try_finally_with_filter_should_show_partial_branch_coverage_when_same_branch_is_covered_and_merged() { createTryFinally(); probes[0] = true; probes[2] = true; runMethodAnalzer(TRY_FINALLY_FILTER); assertLine(1001, 2, 3, 1, 1); } @Test public void try_finally_with_filter_should_show_full_branch_coverage_when_different_branches_are_covered_and_merged() { createTryFinally(); probes[0] = true; probes[3] = true; runMethodAnalzer(TRY_FINALLY_FILTER); assertLine(1001, 2, 3, 0, 2); } // === Scenario: descending line numbers === private void createDescendingLineNumbers() { final Label l0 = new Label(); method.visitLabel(l0); method.visitLineNumber(1003, l0); method.visitInsn(Opcodes.NOP); method.visitInsn(Opcodes.NOP); method.visitInsn(Opcodes.NOP); final Label l1 = new Label(); method.visitLabel(l1); method.visitLineNumber(1002, l1); method.visitInsn(Opcodes.NOP); method.visitInsn(Opcodes.NOP); final Label l2 = new Label(); method.visitLabel(l2); method.visitLineNumber(1001, l2); method.visitInsn(Opcodes.RETURN); } @Test public void decending_line_numbers_should_report_lines_correctly() { createDescendingLineNumbers(); runMethodAnalzer(); assertEquals(1001, result.getFirstLine()); assertEquals(1003, result.getLastLine()); assertLine(1001, 1, 0, 0, 0); assertLine(1002, 2, 0, 0, 0); assertLine(1003, 3, 0, 0, 0); } private void runMethodAnalzer() { runMethodAnalzer(Filters.NONE); } private void runMethodAnalzer(IFilter filter) { LabelFlowAnalyzer.markLabels(method); InstructionsBuilder builder = new InstructionsBuilder(probes); final MethodAnalyzer analyzer = new MethodAnalyzer(builder); final MethodProbesAdapter probesAdapter = new MethodProbesAdapter( analyzer, this); // note that CheckMethodAdapter verifies that this test does not violate // contracts of ASM API analyzer.accept(method, new CheckMethodAdapter(probesAdapter)); MethodCoverageImpl mc = new MethodCoverageImpl("doit", "V()", null); MethodCoverageCalculator mcc = new MethodCoverageCalculator( builder.getInstructions()); filter.filter(method, new FilterContextMock(), mcc); mcc.calculate(mc); result = mc; } private void assertLine(int nr, int insnMissed, int insnCovered, int branchesMissed, int branchesCovered) { final ILine line = result.getLine(nr); assertEquals("Instructions in line " + nr, CounterImpl.getInstance(insnMissed, insnCovered), line.getInstructionCounter()); assertEquals("Branches in line " + nr, CounterImpl.getInstance(branchesMissed, branchesCovered), line.getBranchCounter()); } } MethodCoverageCalculatorTest.java000066400000000000000000000151311451257705100345350ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.junit.Assert.assertEquals; import java.util.Arrays; import java.util.HashMap; import java.util.HashSet; import java.util.Map; import org.jacoco.core.analysis.ISourceNode; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.InsnList; import org.objectweb.asm.tree.InsnNode; /** * Unit tests for {@link MethodCoverageCalculator}. */ public class MethodCoverageCalculatorTest { private Map instructions; // The purpose of this list is to link instruction nodes private InsnList list; private MethodCoverageImpl coverage; @Before public void setup() { instructions = new HashMap(); coverage = new MethodCoverageImpl("run", "()V", null); list = new InsnList(); } @Test public void should_report_instructions() { addInsn(1, true); addInsn(2, true); addInsn(2, false); addInsn(3, false); MethodCoverageCalculator c = new MethodCoverageCalculator(instructions); c.calculate(coverage); assertLine(1, 0, 1, 0, 0); assertLine(2, 1, 1, 0, 0); assertLine(3, 1, 0, 0, 0); } @Test public void should_report_instructions_with_branches() { addInsn(1, false, false); addInsn(2, false, false, true); addInsn(3, false, true, true); MethodCoverageCalculator c = new MethodCoverageCalculator(instructions); c.calculate(coverage); assertLine(1, 1, 0, 2, 0); assertLine(2, 0, 1, 2, 1); assertLine(3, 0, 1, 1, 2); } @Test public void should_ignore_single_instruction() { addInsn(1, true); InsnNode i1 = addInsn(1, false); addInsn(2, true); MethodCoverageCalculator c = new MethodCoverageCalculator(instructions); c.ignore(i1, i1); c.calculate(coverage); assertLine(1, 0, 1, 0, 0); // only one instruction not filtered assertLine(2, 0, 1, 0, 0); } @Test public void should_ignore_instruction_range() { addInsn(1, true); InsnNode i1 = addInsn(2, false); addInsn(2, false); addInsn(2, false); addInsn(2, false); InsnNode i2 = addInsn(2, false); addInsn(3, true); MethodCoverageCalculator c = new MethodCoverageCalculator(instructions); c.ignore(i1, i2); c.calculate(coverage); assertLine(1, 0, 1, 0, 0); assertLine(2, 0, 0, 0, 0); // all instructions filtered in line 2 assertLine(3, 0, 1, 0, 0); } @Test public void should_exclude_ignored_instructions_from_computation_of_first_and_last_lines() { InsnNode i1 = addInsn(1, false); addInsn(2, false); InsnNode i3 = addInsn(3, false); MethodCoverageCalculator c = new MethodCoverageCalculator(instructions); c.ignore(i1, i1); c.ignore(i3, i3); c.calculate(coverage); assertEquals(2, coverage.getFirstLine()); assertEquals(2, coverage.getLastLine()); } @Test public void should_merge_instructions() { addInsn(1, true); InsnNode i1 = addInsn(2, false, true); InsnNode i2 = addInsn(2, true, false); addInsn(3, true); MethodCoverageCalculator c = new MethodCoverageCalculator(instructions); c.merge(i1, i2); c.calculate(coverage); assertLine(1, 0, 1, 0, 0); assertLine(2, 0, 1, 0, 2); // one fully covered instruction left assertLine(3, 0, 1, 0, 0); } @Test public void should_merge_multiple_instructions() { InsnNode i1 = addInsn(1, true, false, false); InsnNode i2 = addInsn(1, false, true, false); InsnNode i3 = addInsn(1, false, false, true); MethodCoverageCalculator c = new MethodCoverageCalculator(instructions); c.merge(i1, i2); c.merge(i2, i3); c.calculate(coverage); assertLine(1, 0, 1, 0, 3); // one fully covered instruction left } @Test public void should_merge_instructions_redundant() { addInsn(1, true); InsnNode i1 = addInsn(2, false, true); InsnNode i2 = addInsn(2, true, false); addInsn(3, true); MethodCoverageCalculator c = new MethodCoverageCalculator(instructions); c.merge(i1, i2); c.merge(i2, i1); c.calculate(coverage); assertLine(1, 0, 1, 0, 0); assertLine(2, 0, 1, 0, 2); // one fully covered instruction left assertLine(3, 0, 1, 0, 0); } @Test public void should_replace_branches() { InsnNode i1 = addInsn(1); InsnNode i2 = addInsn(2, true); InsnNode i3 = addInsn(2, true); InsnNode i4 = addInsn(2, false); MethodCoverageCalculator c = new MethodCoverageCalculator(instructions); c.replaceBranches(i1, new HashSet(Arrays.asList(i2, i3, i4))); c.calculate(coverage); assertLine(1, 0, 1, 1, 2); // branches coverage status replaced assertLine(2, 1, 2, 0, 0); // still in place } @Test public void should_replace_branches_with_merged_instructions() { InsnNode i1 = addInsn(1, false, false, false); InsnNode i2 = addInsn(2, true); InsnNode i3 = addInsn(2, false); InsnNode i4 = addInsn(2, false); MethodCoverageCalculator c = new MethodCoverageCalculator(instructions); c.merge(i4, i3); c.merge(i3, i2); c.replaceBranches(i1, new HashSet(Arrays.asList(i2, i3, i4))); c.calculate(coverage); assertLine(1, 0, 1, 0, 3); } @Test public void should_work_without_lines() { addInsn(ISourceNode.UNKNOWN_LINE, false); addInsn(ISourceNode.UNKNOWN_LINE, false); addInsn(ISourceNode.UNKNOWN_LINE, true); MethodCoverageCalculator c = new MethodCoverageCalculator(instructions); c.calculate(coverage); assertEquals(ISourceNode.UNKNOWN_LINE, coverage.getFirstLine()); assertEquals(ISourceNode.UNKNOWN_LINE, coverage.getLastLine()); assertEquals(CounterImpl.getInstance(2, 1), coverage.getInstructionCounter()); } private void assertLine(int idx, int mi, int ci, int mb, int cb) { assertEquals("instructions", CounterImpl.getInstance(mi, ci), coverage.getLine(idx).getInstructionCounter()); assertEquals("branches", CounterImpl.getInstance(mb, cb), coverage.getLine(idx).getBranchCounter()); } private InsnNode addInsn(int line, boolean... branches) { Instruction i = new Instruction(line); int idx = 0; for (boolean covered : branches) { i.addBranch(covered, idx++); } InsnNode node = new InsnNode(Opcodes.NOP); list.add(node); instructions.put(node, i); return node; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/MethodCoverageImplTest.java000066400000000000000000000113761451257705100334330ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.junit.Assert.assertEquals; import org.jacoco.core.analysis.ICoverageNode; import org.junit.Test; /** * Unit test for {@link MethodCoverageImpl}. */ public class MethodCoverageImplTest { @Test public void testProperties() { // Example: java.util.Collections.emptySet() MethodCoverageImpl node = new MethodCoverageImpl("emptySet", "()Ljava/util/Set;", "()Ljava/util/Set;"); assertEquals(ICoverageNode.ElementType.METHOD, node.getElementType()); assertEquals("emptySet", node.getName()); assertEquals("()Ljava/util/Set;", node.getDesc()); assertEquals("()Ljava/util/Set;", node.getSignature()); } @Test public void testEmptyMethod() { ICoverageNode node = new MethodCoverageImpl("sample", "()V", null); assertEquals(CounterImpl.COUNTER_0_0, node.getInstructionCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getBranchCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getLineCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getComplexityCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getMethodCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getClassCounter()); } @Test public void testIncrementMissedInstructions() { MethodCoverageImpl node = new MethodCoverageImpl("sample", "()V", null); node.increment(CounterImpl.getInstance(25, 0), CounterImpl.COUNTER_0_0, 3); node.incrementMethodCounter(); assertEquals(CounterImpl.COUNTER_1_0, node.getMethodCounter()); assertEquals(CounterImpl.COUNTER_1_0, node.getComplexityCounter()); } @Test public void testIncrementCoveredInstructions() { MethodCoverageImpl node = new MethodCoverageImpl("sample", "()V", null); node.increment(CounterImpl.getInstance(12, 13), CounterImpl.COUNTER_0_0, 3); node.incrementMethodCounter(); assertEquals(CounterImpl.COUNTER_0_1, node.getMethodCounter()); assertEquals(CounterImpl.COUNTER_0_1, node.getComplexityCounter()); } @Test public void testIncrementComplexity1() { MethodCoverageImpl node = new MethodCoverageImpl("sample", "()V", null); node.increment(CounterImpl.COUNTER_0_0, CounterImpl.COUNTER_0_0, 3); assertEquals(CounterImpl.COUNTER_0_0, node.getComplexityCounter()); } @Test public void testIncrementComplexity2() { MethodCoverageImpl node = new MethodCoverageImpl("sample", "()V", null); node.increment(CounterImpl.COUNTER_0_0, CounterImpl.getInstance(2, 0), 3); assertEquals(CounterImpl.getInstance(1, 0), node.getComplexityCounter()); } @Test public void testIncrementComplexity3() { MethodCoverageImpl node = new MethodCoverageImpl("sample", "()V", null); node.increment(CounterImpl.COUNTER_0_0, CounterImpl.getInstance(1, 1), 3); assertEquals(CounterImpl.getInstance(1, 0), node.getComplexityCounter()); } @Test public void testIncrementComplexity4() { MethodCoverageImpl node = new MethodCoverageImpl("sample", "()V", null); node.increment(CounterImpl.COUNTER_0_0, CounterImpl.getInstance(0, 2), 3); assertEquals(CounterImpl.getInstance(0, 1), node.getComplexityCounter()); } @Test public void testIncrementComplexity5() { MethodCoverageImpl node = new MethodCoverageImpl("sample", "()V", null); node.increment(CounterImpl.COUNTER_0_0, CounterImpl.getInstance(3, 0), 3); assertEquals(CounterImpl.getInstance(2, 0), node.getComplexityCounter()); } @Test public void testIncrementComplexity6() { MethodCoverageImpl node = new MethodCoverageImpl("sample", "()V", null); node.increment(CounterImpl.COUNTER_0_0, CounterImpl.getInstance(2, 1), 3); assertEquals(CounterImpl.getInstance(2, 0), node.getComplexityCounter()); } @Test public void testIncrementComplexity7() { MethodCoverageImpl node = new MethodCoverageImpl("sample", "()V", null); node.increment(CounterImpl.COUNTER_0_0, CounterImpl.getInstance(1, 2), 3); assertEquals(CounterImpl.getInstance(1, 1), node.getComplexityCounter()); } @Test public void testIncrementComplexity8() { MethodCoverageImpl node = new MethodCoverageImpl("sample", "()V", null); node.increment(CounterImpl.COUNTER_0_0, CounterImpl.getInstance(0, 3), 3); assertEquals(CounterImpl.getInstance(0, 2), node.getComplexityCounter()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/PackageCoverageTest.java000066400000000000000000000076731451257705100327310ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.junit.Assert.assertEquals; import java.util.Collection; import java.util.Collections; import org.jacoco.core.analysis.IClassCoverage; import org.jacoco.core.analysis.ICoverageNode; import org.jacoco.core.analysis.ISourceFileCoverage; import org.junit.Test; /** * Unit test for {@link PackageCoverageImpl}. */ public class PackageCoverageTest { @Test public void testProperties() { Collection classes = Collections.singleton( (IClassCoverage) new ClassCoverageImpl("org/jacoco/test/Sample", 0, false)); Collection sourceFiles = Collections.singleton( (ISourceFileCoverage) new SourceFileCoverageImpl("Sample.java", "org/jacoco/test/Sample")); PackageCoverageImpl data = new PackageCoverageImpl("org/jacoco/test", classes, sourceFiles); assertEquals(ICoverageNode.ElementType.PACKAGE, data.getElementType()); assertEquals("org/jacoco/test", data.getName()); assertEquals(classes, data.getClasses()); assertEquals(sourceFiles, data.getSourceFiles()); } @Test public void testCountersWithSources() { // Classes with source reference will not considered for counters: final ClassCoverageImpl classnode = new ClassCoverageImpl( "org/jacoco/test/Sample", 0, false) { { classCounter = CounterImpl.getInstance(9, 0); methodCounter = CounterImpl.getInstance(9, 0); branchCounter = CounterImpl.getInstance(9, 0); instructionCounter = CounterImpl.getInstance(9, 0); } }; classnode.setSourceFileName("Sample.java"); // Only source files will be considered for counters: final ISourceFileCoverage sourceFile = new SourceFileCoverageImpl( "Sample.java", "org/jacoco/test/Sample") { { classCounter = CounterImpl.getInstance(1, 0); methodCounter = CounterImpl.getInstance(2, 0); branchCounter = CounterImpl.getInstance(3, 0); instructionCounter = CounterImpl.getInstance(4, 0); } }; PackageCoverageImpl data = new PackageCoverageImpl("org/jacoco/test", Collections.singleton((IClassCoverage) classnode), Collections.singleton(sourceFile)); assertEquals(CounterImpl.getInstance(1, 0), data.getClassCounter()); assertEquals(CounterImpl.getInstance(2, 0), data.getMethodCounter()); assertEquals(CounterImpl.getInstance(3, 0), data.getBranchCounter()); assertEquals(CounterImpl.getInstance(4, 0), data.getInstructionCounter()); } @Test public void testCountersWithoutSources() { // Classes without source reference will be considered for counters: final ClassCoverageImpl classnode = new ClassCoverageImpl( "org/jacoco/test/Sample", 0, false) { { classCounter = CounterImpl.getInstance(1, 0); methodCounter = CounterImpl.getInstance(2, 0); branchCounter = CounterImpl.getInstance(3, 0); instructionCounter = CounterImpl.getInstance(4, 0); } }; final Collection sourceFiles = Collections .emptySet(); PackageCoverageImpl data = new PackageCoverageImpl("org/jacoco/test", Collections.singleton((IClassCoverage) classnode), sourceFiles); assertEquals(CounterImpl.getInstance(1, 0), data.getClassCounter()); assertEquals(CounterImpl.getInstance(2, 0), data.getMethodCounter()); assertEquals(CounterImpl.getInstance(3, 0), data.getBranchCounter()); assertEquals(CounterImpl.getInstance(4, 0), data.getInstructionCounter()); assertEquals(CounterImpl.getInstance(0, 0), data.getLineCounter()); } } SourceFileCoverageImplTest.java000066400000000000000000000020761451257705100341710ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.jacoco.core.analysis.ICoverageNode.ElementType.SOURCEFILE; import static org.junit.Assert.assertEquals; import org.junit.Test; /** * Unit test for {@link SourceFileCoverageImpl}. */ public class SourceFileCoverageImplTest { @Test public void testProperties() { SourceFileCoverageImpl data = new SourceFileCoverageImpl("Sample.java", "org/jacoco/examples"); assertEquals(SOURCEFILE, data.getElementType()); assertEquals("org/jacoco/examples", data.getPackageName()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/SourceNodeImplTest.java000066400000000000000000000144141451257705100326010ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.junit.Assert.assertEquals; import org.jacoco.core.analysis.ICoverageNode.ElementType; import org.jacoco.core.analysis.ISourceNode; import org.junit.Test; /** * Unit tests for {@link SourceNodeImpl}. */ public class SourceNodeImplTest { @Test public void testInit() { final SourceNodeImpl node = new SourceNodeImpl(ElementType.CLASS, "Foo"); assertEquals(ElementType.CLASS, node.getElementType()); assertEquals("Foo", node.getName()); assertEquals(ISourceNode.UNKNOWN_LINE, node.getFirstLine()); assertEquals(ISourceNode.UNKNOWN_LINE, node.getLastLine()); assertEquals(LineImpl.EMPTY, node.getLine(123)); } @Test public void testGetLine() { final SourceNodeImpl node = new SourceNodeImpl(ElementType.CLASS, "Foo"); node.ensureCapacity(10, 20); assertEquals(LineImpl.EMPTY, node.getLine(5)); assertEquals(LineImpl.EMPTY, node.getLine(15)); assertEquals(LineImpl.EMPTY, node.getLine(25)); } @Test public void testEnsureCapacityUnknown1() { final SourceNodeImpl node = new SourceNodeImpl(ElementType.CLASS, "Foo"); node.ensureCapacity(10, ISourceNode.UNKNOWN_LINE); assertEquals(LineImpl.EMPTY, node.getLine(10)); } @Test public void testEnsureCapacityUnknown2() { final SourceNodeImpl node = new SourceNodeImpl(ElementType.CLASS, "Foo"); node.ensureCapacity(ISourceNode.UNKNOWN_LINE, 10); assertEquals(LineImpl.EMPTY, node.getLine(10)); } @Test public void testIncrementLineUnknown() { final SourceNodeImpl node = new SourceNodeImpl(ElementType.CLASS, "Foo"); node.increment(CounterImpl.getInstance(1, 2), CounterImpl.getInstance(3, 4), ISourceNode.UNKNOWN_LINE); assertEquals(CounterImpl.getInstance(1, 2), node.getInstructionCounter()); assertEquals(CounterImpl.getInstance(3, 4), node.getBranchCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getLineCounter()); } @Test public void testIncrementLines() { final SourceNodeImpl node = new SourceNodeImpl(ElementType.CLASS, "Foo"); node.increment(CounterImpl.getInstance(1, 1), CounterImpl.COUNTER_0_0, 10); node.increment(CounterImpl.getInstance(2, 2), CounterImpl.COUNTER_0_0, 12); assertEquals(CounterImpl.getInstance(1, 1), node.getLine(10).getInstructionCounter()); assertEquals(CounterImpl.COUNTER_0_0, node.getLine(11).getInstructionCounter()); assertEquals(CounterImpl.getInstance(2, 2), node.getLine(12).getInstructionCounter()); } @Test public void testIncrementLine1_1() { testIncrementLine(0, 0, 0, 0, 0, 0); } @Test public void testIncrementLine1_2() { testIncrementLine(0, 0, 5, 0, 1, 0); } @Test public void testIncrementLine1_3() { testIncrementLine(0, 0, 0, 5, 0, 1); } @Test public void testIncrementLine1_4() { testIncrementLine(0, 0, 5, 5, 0, 1); } @Test public void testIncrementLine2_1() { testIncrementLine(3, 0, 0, 0, 1, 0); } @Test public void testIncrementLine2_2() { testIncrementLine(3, 0, 5, 0, 1, 0); } @Test public void testIncrementLine2_3() { testIncrementLine(3, 0, 0, 5, 0, 1); } @Test public void testIncrementLine2_4() { testIncrementLine(3, 0, 5, 5, 0, 1); } @Test public void testIncrementLine3_1() { testIncrementLine(0, 3, 0, 0, 0, 1); } @Test public void testIncrementLine3_2() { testIncrementLine(0, 3, 5, 0, 0, 1); } @Test public void testIncrementLine3_3() { testIncrementLine(0, 3, 0, 5, 0, 1); } @Test public void testIncrementLine3_4() { testIncrementLine(0, 3, 5, 5, 0, 1); } @Test public void testIncrementLine4_1() { testIncrementLine(3, 3, 0, 0, 0, 1); } @Test public void testIncrementLine4_2() { testIncrementLine(3, 3, 5, 0, 0, 1); } @Test public void testIncrementLine4_3() { testIncrementLine(3, 3, 0, 5, 0, 1); } @Test public void testIncrementLine4_4() { testIncrementLine(3, 3, 5, 5, 0, 1); } private void testIncrementLine(int mi1, int ci1, int mi2, int ci2, int expectedMissedLines, int expectedCoveredLines) { final SourceNodeImpl node = new SourceNodeImpl(ElementType.CLASS, "Foo"); node.increment(CounterImpl.getInstance(mi1, ci1), CounterImpl.COUNTER_0_0, 33); node.increment(CounterImpl.getInstance(mi2, ci2), CounterImpl.COUNTER_0_0, 33); assertEquals(CounterImpl.getInstance(expectedMissedLines, expectedCoveredLines), node.getLineCounter()); assertEquals(CounterImpl.getInstance(mi1 + mi2, ci1 + ci2), node.getLine(33).getInstructionCounter()); } @Test public void testIncrementChildNoLines() { final SourceNodeImpl node = new SourceNodeImpl(ElementType.CLASS, "Foo"); final SourceNodeImpl child = new SourceNodeImpl(ElementType.CLASS, "Foo") { { this.instructionCounter = CounterImpl.getInstance(1, 11); this.branchCounter = CounterImpl.getInstance(2, 22); this.methodCounter = CounterImpl.getInstance(3, 33); this.classCounter = CounterImpl.getInstance(4, 44); } }; node.increment(child); assertEquals(CounterImpl.getInstance(1, 11), node.getInstructionCounter()); assertEquals(CounterImpl.getInstance(2, 22), node.getBranchCounter()); assertEquals(CounterImpl.getInstance(3, 33), node.getMethodCounter()); assertEquals(CounterImpl.getInstance(4, 44), node.getClassCounter()); } @Test public void testIncrementChildWithLines() { final SourceNodeImpl node = new SourceNodeImpl(ElementType.CLASS, "Foo"); final SourceNodeImpl child = new SourceNodeImpl(ElementType.CLASS, "Foo"); child.increment(CounterImpl.getInstance(1, 11), CounterImpl.getInstance(3, 33), 5); node.increment(child); node.increment(child); assertEquals(CounterImpl.getInstance(2, 22), node.getInstructionCounter()); assertEquals(CounterImpl.getInstance(6, 66), node.getBranchCounter()); assertEquals(CounterImpl.getInstance(0, 1), node.getLineCounter()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/StringPoolTest.java000066400000000000000000000034251451257705100320110ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertSame; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link StringPool}. */ public class StringPoolTest { private StringPool pool; @Before public void setup() { pool = new StringPool(); } @Test public void testGetStringNull() { assertNull(pool.get((String) null)); } @Test public void testGetString() { final String a = pool.get(new String("JaCoCo")); final String b = pool.get(new String("JaCoCo")); assertEquals("JaCoCo", a); assertEquals("JaCoCo", b); assertSame(a, b); } @Test public void testGetArrayNull() { assertNull(pool.get((String[]) null)); } @Test public void testGetEmptyArray() { final String[] arr1 = pool.get(new String[0]); final String[] arr2 = pool.get(new String[0]); assertEquals(0, arr1.length); assertSame(arr1, arr2); } @Test public void testGetArray() { final String[] arr1 = pool.get(new String[] { new String("JaCoCo") }); final String[] arr2 = pool.get(new String[] { new String("JaCoCo") }); assertEquals(1, arr1.length); assertEquals("JaCoCo", arr1[0]); assertSame(arr1[0], arr2[0]); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/000077500000000000000000000000001451257705100274675ustar00rootroot00000000000000AbstractMatcherTest.java000066400000000000000000000205221451257705100341630ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertSame; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; import org.objectweb.asm.tree.VarInsnNode; /** * Unit tests for {@link AbstractMatcher}. */ public class AbstractMatcherTest { private final AbstractMatcher matcher = new AbstractMatcher() { }; private final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "method_name", "()V", null, null); @Test public void skipNonOpcodes() { m.visitFrame(Opcodes.F_FULL, 0, null, 0, null); final Label label = new Label(); m.visitLabel(label); m.visitLineNumber(42, label); m.visitInsn(Opcodes.NOP); // should skip all non opcodes matcher.cursor = m.instructions.getFirst(); matcher.skipNonOpcodes(); assertSame(m.instructions.getLast(), matcher.cursor); // should not change cursor when it points on instruction with opcode matcher.skipNonOpcodes(); assertSame(m.instructions.getLast(), matcher.cursor); // should not do anything when cursor is null matcher.cursor = null; matcher.skipNonOpcodes(); } @Test public void nextIs() { m.visitInsn(Opcodes.NOP); m.visitInsn(Opcodes.NOP); // should set cursor to null when opcode mismatch matcher.cursor = m.instructions.getFirst(); matcher.nextIs(Opcodes.ATHROW); assertNull(matcher.cursor); // should set cursor to next instruction when match matcher.cursor = m.instructions.getFirst(); matcher.nextIs(Opcodes.NOP); assertSame(m.instructions.getLast(), matcher.cursor); // should not do anything when cursor is null matcher.cursor = null; matcher.nextIs(Opcodes.NOP); } @Test public void nextIsSwitch() { // should set cursor to null when opcode mismatch m.visitInsn(Opcodes.NOP); m.visitInsn(Opcodes.NOP); matcher.cursor = m.instructions.getFirst(); matcher.nextIsSwitch(); assertNull(matcher.cursor); // should set cursor to next instruction when match m.instructions.clear(); m.visitInsn(Opcodes.NOP); m.visitTableSwitchInsn(0, 0, new Label()); matcher.cursor = m.instructions.getFirst(); matcher.nextIsSwitch(); assertSame(m.instructions.getLast(), matcher.cursor); // should set cursor to next instruction when match m.instructions.clear(); m.visitInsn(Opcodes.NOP); m.visitLookupSwitchInsn(new Label(), null, new Label[0]); matcher.cursor = m.instructions.getFirst(); matcher.nextIsSwitch(); assertSame(m.instructions.getLast(), matcher.cursor); // should not do anything when cursor is null matcher.cursor = null; matcher.nextIsSwitch(); } @Test public void nextIsVar() { m.visitInsn(Opcodes.NOP); m.visitVarInsn(Opcodes.ILOAD, 42); // should set cursor to null when opcode mismatch matcher.cursor = m.instructions.getFirst(); matcher.nextIsVar(Opcodes.ALOAD, "name"); assertNull(matcher.cursor); // should set cursor to next instruction when match matcher.cursor = m.instructions.getFirst(); matcher.nextIsVar(Opcodes.ILOAD, "name"); assertSame(m.instructions.getLast(), matcher.cursor); // should set cursor to null when var mismatch matcher.cursor = m.instructions.getFirst(); matcher.vars.put("name", new VarInsnNode(Opcodes.ILOAD, 13)); matcher.nextIsVar(Opcodes.ILOAD, "name"); assertNull(matcher.cursor); // should set cursor to next instruction when match matcher.cursor = m.instructions.getFirst(); matcher.vars.put("name", new VarInsnNode(Opcodes.ILOAD, 42)); matcher.nextIsVar(Opcodes.ILOAD, "name"); assertSame(m.instructions.getLast(), matcher.cursor); // should not do anything when cursor is null matcher.cursor = null; matcher.nextIsVar(Opcodes.ILOAD, "name"); } @Test public void nextIsField() { m.visitInsn(Opcodes.NOP); m.visitFieldInsn(Opcodes.PUTSTATIC, "owner", "name", "Z"); // should set cursor to null when opcode mismatch matcher.cursor = m.instructions.getFirst(); matcher.nextIsField(Opcodes.GETSTATIC, "owner", "name", "Z"); assertNull(matcher.cursor); // should set cursor to null when owner mismatch matcher.cursor = m.instructions.getFirst(); matcher.nextIsField(Opcodes.PUTSTATIC, "another_owner", "name", "Z"); assertNull(matcher.cursor); // should set cursor to null when name mismatch matcher.cursor = m.instructions.getFirst(); matcher.nextIsField(Opcodes.PUTSTATIC, "owner", "another_name", "Z"); assertNull(matcher.cursor); // should set cursor to null when descriptor mismatch matcher.cursor = m.instructions.getFirst(); matcher.nextIsField(Opcodes.PUTSTATIC, "owner", "name", "another_descriptor"); assertNull(matcher.cursor); // should set cursor to next instruction when match matcher.cursor = m.instructions.getFirst(); matcher.nextIsField(Opcodes.PUTSTATIC, "owner", "name", "Z"); assertSame(m.instructions.getLast(), matcher.cursor); // should not do anything when cursor is null matcher.cursor = null; matcher.nextIsField(Opcodes.PUTSTATIC, "owner", "name", "Z"); } @Test public void nextIsInvoke() { m.visitInsn(Opcodes.NOP); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "owner", "name", "()V", false); // should set cursor to null when opcode mismatch matcher.cursor = m.instructions.getFirst(); matcher.nextIsInvoke(Opcodes.INVOKESTATIC, "owner", "name", "()V"); assertNull(matcher.cursor); // should set cursor to null when owner mismatch matcher.cursor = m.instructions.getFirst(); matcher.nextIsInvoke(Opcodes.INVOKEVIRTUAL, "another_owner", "name", "()V"); assertNull(matcher.cursor); // should set cursor to null when name mismatch matcher.cursor = m.instructions.getFirst(); matcher.nextIsInvoke(Opcodes.INVOKEVIRTUAL, "owner", "another_name", "()V"); assertNull(matcher.cursor); // should set cursor to null when descriptor mismatch matcher.cursor = m.instructions.getFirst(); matcher.nextIsInvoke(Opcodes.INVOKEVIRTUAL, "owner", "name", "(Lanother_descriptor;)V"); assertNull(matcher.cursor); // should set cursor to next instruction when match matcher.cursor = m.instructions.getFirst(); matcher.nextIsInvoke(Opcodes.INVOKEVIRTUAL, "owner", "name", "()V"); assertSame(m.instructions.getLast(), matcher.cursor); // should not do anything when cursor is null matcher.cursor = null; matcher.nextIsInvoke(Opcodes.INVOKEVIRTUAL, "owner", "name", "()V"); } @Test public void nextIsType() { m.visitInsn(Opcodes.NOP); m.visitTypeInsn(Opcodes.NEW, "descriptor"); // should set cursor to null when opcode mismatch matcher.cursor = m.instructions.getFirst(); matcher.nextIsType(Opcodes.CHECKCAST, "descriptor"); assertNull(matcher.cursor); // should set cursor to null when descriptor mismatch matcher.cursor = m.instructions.getFirst(); matcher.nextIsType(Opcodes.NEW, "another_descriptor"); assertNull(matcher.cursor); // should set cursor to next instruction when match matcher.cursor = m.instructions.getFirst(); matcher.nextIsType(Opcodes.NEW, "descriptor"); assertSame(m.instructions.getLast(), matcher.cursor); // should not do anything when cursor is null matcher.cursor = null; matcher.nextIsType(Opcodes.NEW, "descriptor"); } @Test public void firstIsALoad0() { // should set cursor to null when no opcodes are present matcher.firstIsALoad0(m); assertNull(matcher.cursor); // should set cursor to null when opcode mismatch m.visitInsn(Opcodes.NOP); matcher.firstIsALoad0(m); assertNull(matcher.cursor); // should set cursor to null when var mismatch m.instructions.clear(); m.visitVarInsn(Opcodes.ALOAD, 1); matcher.firstIsALoad0(m); assertNull(matcher.cursor); // should set cursor to first instruction when match m.instructions.clear(); m.visitVarInsn(Opcodes.ALOAD, 0); matcher.firstIsALoad0(m); assertSame(m.instructions.getLast(), matcher.cursor); } } AnnotationGeneratedFilterTest.java000066400000000000000000000070551451257705100362210ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link AnnotationGeneratedFilter}. */ public class AnnotationGeneratedFilterTest extends FilterTestBase { private final IFilter filter = new AnnotationGeneratedFilter(); @Test public void should_filter_methods_annotated_with_runtime_visible_org_groovy_transform_Generated() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()I", null, null); m.visitAnnotation("Lgroovy/transform/Generated;", true); m.visitInsn(Opcodes.ICONST_0); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_filter_methods_annotated_with_runtime_invisible_lombok_Generated() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()I", null, null); m.visitAnnotation("Llombok/Generated;", false); m.visitInsn(Opcodes.ICONST_0); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_filter_classes_annotated_with_runtime_visible_org_immutables_value_Generated() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()I", null, null); m.visitInsn(Opcodes.ICONST_0); m.visitInsn(Opcodes.IRETURN); context.classAnnotations.add("Lorg/immutables/value/Generated;"); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_filter_classes_annotated_with_runtime_visible_org_apache_avro_specific_AvroGenerated() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "readExternal", "()V", null, null); m.visitInsn(Opcodes.NOP); context.classAnnotations .add("Lorg/apache/avro/specific/AvroGenerated;"); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_filter_when_annotation_is_inner() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()I", null, null); m.visitInsn(Opcodes.ICONST_0); m.visitInsn(Opcodes.IRETURN); context.classAnnotations.add("Lorg/example/Class$Generated;"); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_not_filter_when_no_annotations() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()I", null, null); m.visitInsn(Opcodes.ICONST_0); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_when_other_annotations() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()I", null, null); m.visitAnnotation("LOtherAnnotation;", true); m.visitInsn(Opcodes.ICONST_0); m.visitInsn(Opcodes.IRETURN); context.classAnnotations.add("LOtherAnnotation;"); filter.filter(m, context, output); assertIgnored(); } } AssertFilterTest.java000066400000000000000000000100671451257705100335260ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.Type; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link AssertFilter}. */ public class AssertFilterTest extends FilterTestBase { private final AssertFilter filter = new AssertFilter(); /** *
	 * class Example {
	 *   void example(boolean b) {
	 *     ...
	 *     assert b : "message";
	 *     ...
	 *   }
	 * }
	 * 
*/ @Test public void should_filter_static_initializer() { context.className = "Example"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_STATIC, "", "()V", null, null); m.visitLdcInsn(Type.getType("LExample;")); final Range range = new Range(); range.fromInclusive = m.instructions.getLast(); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Class", "desiredAssertionStatus", "()Z", false); final Label label1 = new Label(); final Label label2 = new Label(); m.visitJumpInsn(Opcodes.IFNE, label1); m.visitInsn(Opcodes.ICONST_1); m.visitJumpInsn(Opcodes.GOTO, label2); m.visitLabel(label1); m.visitInsn(Opcodes.ICONST_0); m.visitLabel(label2); m.visitFieldInsn(Opcodes.PUTSTATIC, "Example", "$assertionsDisabled", "Z"); range.toInclusive = m.instructions.getLast(); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(range); } /** *
	 * class Example {
	 *   static final f;
	 *
	 *   static {
	 *     f = !Example.class.desiredAssertionStatus();
	 *   }
	 * }
	 * 
*/ @Test public void should_not_filter_static_initializer_when_field_name_does_not_match() { context.className = "Example"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_STATIC, "", "()V", null, null); m.visitLdcInsn(Type.getType("LExample;")); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Class", "desiredAssertionStatus", "()Z", false); final Label label1 = new Label(); final Label label2 = new Label(); m.visitJumpInsn(Opcodes.IFNE, label1); m.visitInsn(Opcodes.ICONST_1); m.visitJumpInsn(Opcodes.GOTO, label2); m.visitLabel(label1); m.visitInsn(Opcodes.ICONST_0); m.visitLabel(label2); m.visitFieldInsn(Opcodes.PUTSTATIC, "Foo", "f", "Z"); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(); } /** *
	 * class Example {
	 *   void example(boolean b) {
	 *     ...
	 *     assert b : "message";
	 *     ...
	 *   }
	 * }
	 * 
*/ @Test public void should_filter_assert() { context.className = "Example"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "example", "()V", null, null); m.visitInsn(Opcodes.NOP); m.visitFieldInsn(Opcodes.GETSTATIC, "Example", "$assertionsDisabled", "Z"); final Label label = new Label(); m.visitJumpInsn(Opcodes.IFNE, label); final Range range = new Range(m.instructions.getLast(), m.instructions.getLast()); m.visitVarInsn(Opcodes.ILOAD, 1); m.visitJumpInsn(Opcodes.IFNE, label); m.visitTypeInsn(Opcodes.NEW, "java/lang/AssertionError"); m.visitInsn(Opcodes.DUP); m.visitLdcInsn("message"); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/AssertionError", "", "(Ljava/lang/Object;)V", false); m.visitInsn(Opcodes.ATHROW); m.visitLabel(label); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(range); } } BridgeFilterTest.java000066400000000000000000000026561451257705100334660ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link BridgeFilter}. */ public class BridgeFilterTest extends FilterTestBase { private final BridgeFilter filter = new BridgeFilter(); @Test public void should_filter_bridge_methods() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_BRIDGE, "m", "()Ljava/lang/Object;", null, null); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_not_filter_non_bridge_methods() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "m", "()Ljava/lang/Object;", null, null); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(); } } EnumEmptyConstructorFilterTest.java000066400000000000000000000071741451257705100364630ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link EnumEmptyConstructorFilter}. */ public class EnumEmptyConstructorFilterTest extends FilterTestBase { private final EnumEmptyConstructorFilter filter = new EnumEmptyConstructorFilter(); @Test public void should_filter() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_PRIVATE, "", "(Ljava/lang/String;I)V", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ILOAD, 2); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/Enum", "", "(Ljava/lang/String;I)V", false); m.visitInsn(Opcodes.RETURN); context.superClassName = "java/lang/Enum"; filter.filter(m, context, output); assertIgnored( new Range(m.instructions.getFirst(), m.instructions.getLast())); } /** *
	 * enum E {
	 *   ;
	 *   private E() {
	 *     ...
	 *   }
	 * }
	 * 
*/ @Test public void should_not_filter_non_empty_constructor() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_PRIVATE, "", "(Ljava/lang/String;I)V", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ILOAD, 2); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/Enum", "", "(Ljava/lang/String;I)V", false); m.visitInsn(Opcodes.NOP); m.visitInsn(Opcodes.RETURN); context.superClassName = "java/lang/Enum"; filter.filter(m, context, output); assertIgnored(); } /** *
	 * enum E {
	 *   ;
	 *   private E(long p) {
	 *   }
	 * }
	 * 
*/ @Test public void should_not_filter_constructor_with_additional_parameters() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_PRIVATE, "", "(Ljava/lang/String;IJ)V", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ILOAD, 2); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/Enum", "", "(Ljava/lang/String;I)V", false); m.visitInsn(Opcodes.RETURN); context.superClassName = "java/lang/Enum"; filter.filter(m, context, output); assertIgnored(); } /** *
	 * enum E {
	 *   ;
	 *   private void method(String p1, int p2) {
	 *   }
	 * }
	 * 
*/ @Test public void should_not_filter_non_constructor() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_PRIVATE, "method", "(Ljava/lang/String;I)V", null, null); m.visitInsn(Opcodes.NOP); context.superClassName = "java/lang/Enum"; filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_non_Enum() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_PRIVATE, "", "(Ljava/lang/String;I)V", null, null); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/EnumFilterTest.java000066400000000000000000000042741451257705100332530ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link EnumFilter}. */ public class EnumFilterTest extends FilterTestBase { private final EnumFilter filter = new EnumFilter(); @Test public void testValues() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "values", "()[LFoo;", null, null); m.visitInsn(Opcodes.NOP); context.superClassName = "java/lang/Enum"; filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void testNonValues() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "values", "()V", null, null); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(); } @Test public void testValueOf() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "valueOf", "(Ljava/lang/String;)LFoo;", null, null); m.visitInsn(Opcodes.NOP); context.superClassName = "java/lang/Enum"; filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void testNonValueOf() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "valueOf", "()V", null, null); m.visitInsn(Opcodes.NOP); context.superClassName = "java/lang/Enum"; filter.filter(m, context, output); assertIgnored(); } @Test public void testNonEnum() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "values", "()[LFoo;", null, null); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(); } } ExhaustiveSwitchFilterTest.java000066400000000000000000000213471451257705100355770ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.MethodNode; import java.util.HashSet; import java.util.Set; /** * Unit tests for {@link ExhaustiveSwitchFilter}. */ public class ExhaustiveSwitchFilterTest extends FilterTestBase { private final IFilter filter = new ExhaustiveSwitchFilter(); /** *
	 *   enum E {
	 *     A, B, C
	 *   }
	 *
	 *   int example(E e) {
	 *     return switch (e) {
	 *       case A -> 1;
	 *       case B -> 2;
	 *       case C -> 3;
	 *     };
	 *   }
	 * 
*/ @Test public void should_filter_when_default_branch_has_LineNumber_of_switch() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "Example", "()I", null, null); final Label start = new Label(); final Label end = new Label(); m.visitLabel(start); m.visitLineNumber(0, start); m.visitFieldInsn(Opcodes.GETSTATIC, "Example$1", "$SwitchMap$Example$E", "[I"); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Example$E", "ordinal", "()I", false); m.visitInsn(Opcodes.IALOAD); final Label dflt = new Label(); final Label case1 = new Label(); final Label case2 = new Label(); final Label case3 = new Label(); m.visitLookupSwitchInsn(dflt, new int[] { 1, 2, 3 }, new Label[] { case1, case2, case3 }); final AbstractInsnNode switchNode = m.instructions.getLast(); final Set newTargets = new HashSet(); m.visitLabel(dflt); final Range range = new Range(); range.fromInclusive = m.instructions.getLast(); m.visitLineNumber(0, dflt); m.visitTypeInsn(Opcodes.NEW, "java/lang/IncompatibleClassChangeError"); m.visitInsn(Opcodes.DUP); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/IncompatibleClassChangeError", "", "()V", false); m.visitInsn(Opcodes.ATHROW); range.toInclusive = m.instructions.getLast(); m.visitLabel(case1); m.visitInsn(Opcodes.ICONST_1); newTargets.add(m.instructions.getLast()); m.visitJumpInsn(Opcodes.GOTO, end); m.visitLabel(case2); m.visitInsn(Opcodes.ICONST_2); newTargets.add(m.instructions.getLast()); m.visitLabel(case3); m.visitInsn(Opcodes.ICONST_3); newTargets.add(m.instructions.getLast()); m.visitLabel(end); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertIgnored(range); assertReplacedBranches(switchNode, newTargets); } /** *
	 *   enum E {
	 *     A, B, C
	 *   }
	 *
	 *   int example(E e) {
	 *     return switch (e) {
	 *       case A -> 1;
	 *       case B -> 2;
	 *       case C -> 3;
	 *     };
	 *   }
	 * 
*/ @Test public void should_filter_when_default_branch_has_no_LineNumber() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "Example", "()I", null, null); final Label start = new Label(); final Label end = new Label(); m.visitLabel(start); m.visitLineNumber(0, start); m.visitFieldInsn(Opcodes.GETSTATIC, "Example$1", "$SwitchMap$Example$E", "[I"); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Example$E", "ordinal", "()I", false); m.visitInsn(Opcodes.IALOAD); final Label dflt = new Label(); final Label case1 = new Label(); final Label case2 = new Label(); final Label case3 = new Label(); m.visitLookupSwitchInsn(dflt, new int[] { 1, 2, 3 }, new Label[] { case1, case2, case3 }); final AbstractInsnNode switchNode = m.instructions.getLast(); final Set newTargets = new HashSet(); m.visitLabel(dflt); final Range range = new Range(); range.fromInclusive = m.instructions.getLast(); m.visitTypeInsn(Opcodes.NEW, "java/lang/IncompatibleClassChangeError"); m.visitInsn(Opcodes.DUP); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/IncompatibleClassChangeError", "", "()V", false); m.visitInsn(Opcodes.ATHROW); range.toInclusive = m.instructions.getLast(); m.visitLabel(case1); m.visitInsn(Opcodes.ICONST_1); newTargets.add(m.instructions.getLast()); m.visitJumpInsn(Opcodes.GOTO, end); m.visitLabel(case2); m.visitInsn(Opcodes.ICONST_2); newTargets.add(m.instructions.getLast()); m.visitLabel(case3); m.visitInsn(Opcodes.ICONST_3); newTargets.add(m.instructions.getLast()); m.visitLabel(end); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertIgnored(range); assertReplacedBranches(switchNode, newTargets); } /** *
	 *   enum E {
	 *     A, B, C
	 *   }
	 *
	 *   int example(E e) {
	 *     return switch (e) {
	 *       case A -> 1;
	 *       case B -> 2;
	 *       case C -> 3;
	 *     };
	 *   }
	 * 
*/ @Test public void should_filter_when_default_branch_throws_Java_21_MatchException() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "Example", "()I", null, null); final Label start = new Label(); final Label end = new Label(); m.visitLabel(start); m.visitLineNumber(0, start); m.visitFieldInsn(Opcodes.GETSTATIC, "Example$1", "$SwitchMap$Example$E", "[I"); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Example$E", "ordinal", "()I", false); m.visitInsn(Opcodes.IALOAD); final Label dflt = new Label(); final Label case1 = new Label(); final Label case2 = new Label(); final Label case3 = new Label(); m.visitLookupSwitchInsn(dflt, new int[] { 1, 2, 3 }, new Label[] { case1, case2, case3 }); final AbstractInsnNode switchNode = m.instructions.getLast(); final Set newTargets = new HashSet(); m.visitLabel(dflt); final Range range = new Range(); range.fromInclusive = m.instructions.getLast(); m.visitTypeInsn(Opcodes.NEW, "java/lang/MatchException"); m.visitInsn(Opcodes.DUP); m.visitInsn(Opcodes.ACONST_NULL); m.visitInsn(Opcodes.ACONST_NULL); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/MatchException", "", "(Ljava/lang/String;Ljava/lang/Throwable;)V", false); m.visitInsn(Opcodes.ATHROW); range.toInclusive = m.instructions.getLast(); m.visitLabel(case1); m.visitInsn(Opcodes.ICONST_1); newTargets.add(m.instructions.getLast()); m.visitJumpInsn(Opcodes.GOTO, end); m.visitLabel(case2); m.visitInsn(Opcodes.ICONST_2); newTargets.add(m.instructions.getLast()); m.visitLabel(case3); m.visitInsn(Opcodes.ICONST_3); newTargets.add(m.instructions.getLast()); m.visitLabel(end); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertIgnored(range); assertReplacedBranches(switchNode, newTargets); } /** *
	 *   enum E {
	 *     A, B, C
	 *   }
	 *
	 *   int example(E e) {
	 *     return switch (e) {
	 *       case A -> 1;
	 *       case B -> 2;
	 *       default -> throw new IncompatibleClassChangeError();
	 *     };
	 *   }
	 * 
*/ @Test public void should_not_filter_when_default_branch_has_LineNumber_different_from_switch() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "Example", "()I", null, null); final Label start = new Label(); final Label end = new Label(); m.visitLabel(start); m.visitLineNumber(0, start); m.visitFieldInsn(Opcodes.GETSTATIC, "Example$1", "$SwitchMap$Example$E", "[I"); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Example$E", "ordinal", "()I", false); m.visitInsn(Opcodes.IALOAD); final Label dflt = new Label(); final Label case1 = new Label(); final Label case2 = new Label(); m.visitLookupSwitchInsn(dflt, new int[] { 1, 2 }, new Label[] { case1, case2 }); m.visitLabel(dflt); m.visitLineNumber(1, dflt); m.visitTypeInsn(Opcodes.NEW, "java/lang/IncompatibleClassChangeError"); m.visitInsn(Opcodes.DUP); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/IncompatibleClassChangeError", "", "()V", false); m.visitInsn(Opcodes.ATHROW); m.visitLabel(case1); m.visitInsn(Opcodes.ICONST_1); m.visitJumpInsn(Opcodes.GOTO, end); m.visitLabel(case2); m.visitInsn(Opcodes.ICONST_2); m.visitLabel(end); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertIgnored(); } } FilterContextMock.java000066400000000000000000000026611451257705100336640ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import java.util.HashSet; import java.util.Set; /** * {@link IFilterContext} mock for unit tests. */ public class FilterContextMock implements IFilterContext { public String className = "Foo"; public String superClassName = "java/lang/Object"; public Set classAnnotations = new HashSet(); public Set classAttributes = new HashSet(); public String sourceFileName = "Foo.java"; public String sourceDebugExtension; public String getClassName() { return className; } public String getSuperClassName() { return superClassName; } public Set getClassAnnotations() { return classAnnotations; } public Set getClassAttributes() { return classAttributes; } public String getSourceFileName() { return sourceFileName; } public String getSourceDebugExtension() { return sourceDebugExtension; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/FilterTestBase.java000066400000000000000000000057221451257705100332200ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import static org.junit.Assert.assertArrayEquals; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.util.ArrayList; import java.util.Collections; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.Set; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.MethodNode; /** * Base class for tests of {@link IFilter} implementations. */ public abstract class FilterTestBase { protected final FilterContextMock context = new FilterContextMock(); private final List ignoredRanges = new ArrayList(); private final Map> replacedBranches = new HashMap>(); protected final IFilterOutput output = new IFilterOutput() { public void ignore(final AbstractInsnNode fromInclusive, final AbstractInsnNode toInclusive) { final Range range = new Range(); range.fromInclusive = fromInclusive; range.toInclusive = toInclusive; ignoredRanges.add(range); } public void merge(final AbstractInsnNode i1, final AbstractInsnNode i2) { fail(); } public void replaceBranches(final AbstractInsnNode source, final Set newTargets) { replacedBranches.put(source, newTargets); } }; final void assertIgnored(Range... ranges) { assertArrayEquals(ranges, ignoredRanges.toArray(new Range[0])); } final void assertMethodIgnored(final MethodNode m) { assertIgnored( new Range(m.instructions.getFirst(), m.instructions.getLast())); } final void assertNoReplacedBranches() { assertTrue(replacedBranches.isEmpty()); } final void assertReplacedBranches(final AbstractInsnNode source, final Set newTargets) { assertEquals(Collections.singletonMap(source, newTargets), replacedBranches); } static class Range { AbstractInsnNode fromInclusive; AbstractInsnNode toInclusive; Range() { } Range(AbstractInsnNode fromInclusive, AbstractInsnNode toInclusive) { this.fromInclusive = fromInclusive; this.toInclusive = toInclusive; } @Override public boolean equals(Object obj) { if (obj.getClass() == Range.class) { final Range other = (Range) obj; return this.fromInclusive.equals(other.fromInclusive) && this.toInclusive.equals(other.toInclusive); } return false; } } } FinallyFilterTest.java000066400000000000000000000265511451257705100336700ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import static org.junit.Assert.assertEquals; import static org.junit.Assert.fail; import java.util.HashSet; import java.util.Set; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link FinallyFilter}. */ public class FinallyFilterTest implements IFilterOutput { private final IFilter filter = new FinallyFilter(); private final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "()V", null, null); /** *
	 *   try {
	 *     ...
	 *     if (...) {
	 *       ...
	 *       return;
	 *     } else {
	 *       ...
	 *       return;
	 *     }
	 *   } finally {
	 *     ...
	 *   }
	 * 
*/ @Test public void should_analyze_control_flow() { final Label start1 = new Label(); final Label end1 = new Label(); final Label start2 = new Label(); final Label end2 = new Label(); final Label finallyStart = new Label(); m.visitTryCatchBlock(start1, end1, finallyStart, null); m.visitTryCatchBlock(start2, end2, finallyStart, null); m.visitLabel(start1); // jump to another region associated with same handler: m.visitJumpInsn(Opcodes.IFEQ, start2); m.visitInsn(Opcodes.NOP); m.visitLabel(end1); m.visitInsn(Opcodes.NOP); // finally block shouldMergeLast(); m.visitInsn(Opcodes.RETURN); m.visitLabel(start2); m.visitInsn(Opcodes.NOP); m.visitLabel(end2); m.visitInsn(Opcodes.NOP); // finally block shouldMergeLast(); m.visitInsn(Opcodes.RETURN); m.visitLabel(finallyStart); m.visitVarInsn(Opcodes.ASTORE, 1); shouldIgnoreLast(); m.visitInsn(Opcodes.NOP); // finally block shouldMergeLast(); m.visitVarInsn(Opcodes.ALOAD, 1); shouldIgnoreLast(); m.visitInsn(Opcodes.ATHROW); shouldIgnoreLast(); execute(); } // === try/catch/finally === @Test public void javac_try_catch_finally() { final Label tryStart = new Label(); final Label tryEnd = new Label(); final Label catchStart = new Label(); final Label catchEnd = new Label(); final Label finallyStart = new Label(); final Label finallyEnd = new Label(); m.visitTryCatchBlock(tryStart, tryEnd, catchStart, "java/lang/Exception"); m.visitTryCatchBlock(catchStart, catchEnd, finallyStart, null); m.visitTryCatchBlock(tryStart, tryEnd, finallyStart, null); m.visitLabel(tryStart); m.visitInsn(Opcodes.NOP); // try body m.visitLabel(tryEnd); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitJumpInsn(Opcodes.GOTO, finallyEnd); shouldIgnoreLast(); m.visitLabel(catchStart); m.visitInsn(Opcodes.NOP); // catch body m.visitLabel(catchEnd); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitInsn(Opcodes.ATHROW); m.visitLabel(finallyStart); m.visitVarInsn(Opcodes.ASTORE, 1); shouldIgnoreLast(); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitVarInsn(Opcodes.ALOAD, 1); shouldIgnoreLast(); m.visitInsn(Opcodes.ATHROW); shouldIgnoreLast(); m.visitLabel(finallyEnd); m.visitInsn(Opcodes.NOP); execute(); } @Test public void ecj_try_catch_finally() { final Label tryStart = new Label(); final Label tryEnd = new Label(); final Label catchStart = new Label(); final Label catchEnd = new Label(); final Label finallyStart = new Label(); final Label finallyEnd = new Label(); final Label after = new Label(); m.visitTryCatchBlock(tryStart, tryEnd, catchStart, "java/lang/Exception"); m.visitTryCatchBlock(tryStart, catchEnd, finallyStart, null); m.visitLabel(tryStart); m.visitInsn(Opcodes.NOP); // try body m.visitLabel(tryEnd); m.visitJumpInsn(Opcodes.GOTO, finallyEnd); m.visitLabel(catchStart); m.visitInsn(Opcodes.POP); m.visitInsn(Opcodes.NOP); // catch body m.visitLabel(catchEnd); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitJumpInsn(Opcodes.GOTO, after); shouldIgnoreLast(); m.visitLabel(finallyStart); m.visitVarInsn(Opcodes.ASTORE, 1); shouldIgnoreLast(); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitVarInsn(Opcodes.ALOAD, 1); shouldIgnoreLast(); m.visitInsn(Opcodes.ATHROW); shouldIgnoreLast(); m.visitLabel(finallyEnd); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitLabel(after); m.visitInsn(Opcodes.NOP); execute(); } // === empty catch === /** * javac 1.5 - 1.7 */ @Test public void javac_empty_catch() { final Label tryStart = new Label(); final Label tryEnd = new Label(); final Label catchStart = new Label(); final Label catchEnd = new Label(); final Label finallyStart = new Label(); final Label finallyEnd = new Label(); m.visitTryCatchBlock(tryStart, tryEnd, catchStart, "java/lang/Exception"); m.visitTryCatchBlock(tryStart, tryEnd, finallyStart, null); m.visitTryCatchBlock(catchStart, catchEnd, finallyStart, null); // actually one more useless TryCatchBlock for ASTORE in finally m.visitLabel(tryStart); m.visitInsn(Opcodes.NOP); // try body m.visitLabel(tryEnd); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitJumpInsn(Opcodes.GOTO, finallyEnd); shouldIgnoreLast(); m.visitLabel(catchStart); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitLabel(catchEnd); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitJumpInsn(Opcodes.GOTO, finallyEnd); shouldIgnoreLast(); m.visitLabel(finallyStart); m.visitVarInsn(Opcodes.ASTORE, 1); shouldIgnoreLast(); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitVarInsn(Opcodes.ALOAD, 1); shouldIgnoreLast(); m.visitInsn(Opcodes.ATHROW); shouldIgnoreLast(); m.visitLabel(finallyEnd); m.visitInsn(Opcodes.NOP); execute(); } /** * javac >= 1.8 * * Probably related to https://bugs.openjdk.java.net/browse/JDK-7093325 */ @Test public void javac_8_empty_catch() throws Exception { final Label tryStart = new Label(); final Label tryEnd = new Label(); final Label catchStart = new Label(); final Label finallyStart = new Label(); final Label finallyEnd = new Label(); m.visitTryCatchBlock(tryStart, tryEnd, catchStart, "java/lang/Exception"); m.visitTryCatchBlock(tryStart, tryEnd, finallyStart, null); m.visitLabel(tryStart); m.visitInsn(Opcodes.NOP); // try body m.visitLabel(tryEnd); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitJumpInsn(Opcodes.GOTO, finallyEnd); shouldIgnoreLast(); shouldIgnoreLast(); m.visitLabel(catchStart); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitJumpInsn(Opcodes.GOTO, finallyEnd); shouldIgnoreLast(); m.visitLabel(finallyStart); m.visitVarInsn(Opcodes.ASTORE, 1); shouldIgnoreLast(); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitVarInsn(Opcodes.ALOAD, 1); shouldIgnoreLast(); m.visitInsn(Opcodes.ATHROW); shouldIgnoreLast(); m.visitLabel(finallyEnd); execute(); } @Test public void ecj_empty_catch() { final Label tryStart = new Label(); final Label tryEnd = new Label(); final Label catchStart = new Label(); final Label catchEnd = new Label(); final Label finallyStart = new Label(); final Label finallyEnd = new Label(); final Label after = new Label(); m.visitTryCatchBlock(tryStart, tryEnd, catchStart, "java/lang/Exception"); m.visitTryCatchBlock(tryStart, catchEnd, finallyStart, null); m.visitLabel(tryStart); m.visitInsn(Opcodes.NOP); // try body m.visitLabel(tryEnd); m.visitJumpInsn(Opcodes.GOTO, finallyEnd); m.visitLabel(catchStart); m.visitInsn(Opcodes.POP); m.visitLabel(catchEnd); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitJumpInsn(Opcodes.GOTO, after); shouldIgnoreLast(); m.visitLabel(finallyStart); m.visitVarInsn(Opcodes.ASTORE, 1); shouldIgnoreLast(); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitVarInsn(Opcodes.ALOAD, 1); shouldIgnoreLast(); m.visitInsn(Opcodes.ATHROW); shouldIgnoreLast(); m.visitLabel(finallyEnd); m.visitInsn(Opcodes.NOP); // finally body shouldMergeLast(); m.visitLabel(after); m.visitInsn(Opcodes.NOP); execute(); } // === always completes abruptly === @Test public void javac_always_completes_abruptly() { final Label tryStart = new Label(); final Label tryEnd = new Label(); final Label finallyStart = new Label(); m.visitTryCatchBlock(tryStart, tryEnd, finallyStart, null); m.visitLabel(tryStart); m.visitInsn(Opcodes.NOP); // try body m.visitLabel(tryEnd); m.visitInsn(Opcodes.RETURN); // finally body m.visitLabel(finallyStart); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitInsn(Opcodes.RETURN); // finally body execute(); } @Test public void ecj_always_completes_abruptly() { final Label tryStart = new Label(); final Label tryEnd = new Label(); final Label finallyStart = new Label(); m.visitTryCatchBlock(tryStart, tryEnd, tryEnd, null); m.visitLabel(tryStart); m.visitInsn(Opcodes.NOP); // try body m.visitJumpInsn(Opcodes.GOTO, finallyStart); m.visitLabel(tryEnd); m.visitInsn(Opcodes.POP); m.visitLabel(finallyStart); m.visitInsn(Opcodes.RETURN); // finally body execute(); } private final Set expectedIgnored = new HashSet(); private final Set actualIgnored = new HashSet(); private final Set expectedMerged = new HashSet(); private final Set actualMerged = new HashSet(); private void shouldMergeLast() { expectedMerged.add(m.instructions.getLast()); } private void shouldIgnoreLast() { expectedIgnored.add(m.instructions.getLast()); } private void execute() { filter.filter(m, new FilterContextMock(), this); assertEquals("ignored", toIndexes(expectedIgnored), toIndexes(actualIgnored)); assertEquals("merged", toIndexes(expectedMerged), toIndexes(actualMerged)); } @SuppressWarnings("boxing") private Set toIndexes(Set set) { final Set result = new HashSet(); for (final AbstractInsnNode i : set) { result.add(m.instructions.indexOf(i)); } return result; } public void ignore(final AbstractInsnNode fromInclusive, final AbstractInsnNode toInclusive) { for (AbstractInsnNode i = fromInclusive; i != toInclusive; i = i .getNext()) { actualIgnored.add(i); } actualIgnored.add(toInclusive); } public void merge(final AbstractInsnNode i1, final AbstractInsnNode i2) { if (actualMerged.isEmpty() || actualMerged.contains(i1) || actualMerged.contains(i2)) { actualMerged.add(i1); actualMerged.add(i2); } else { fail(); } } public void replaceBranches(final AbstractInsnNode source, final Set newTargets) { fail(); } } KotlinCoroutineFilterTest.java000066400000000000000000000352201451257705100354130ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit test for {@link KotlinCoroutineFilter}. */ public class KotlinCoroutineFilterTest extends FilterTestBase { private final IFilter filter = new KotlinCoroutineFilter(); @Test public void should_filter_suspending_lambdas_generated_by_Kotlin_1_3_30() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "invokeSuspend", "(Ljava/lang/Object;)Ljava/lang/Object;", null, null); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); m.visitMethodInsn(Opcodes.INVOKESTATIC, "kotlin/coroutines/intrinsics/IntrinsicsKt", "getCOROUTINE_SUSPENDED", "()Ljava/lang/Object;", false); final Range range1 = new Range(); range1.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 4); m.visitVarInsn(Opcodes.ALOAD, 0); // line of "runBlocking" m.visitFieldInsn(Opcodes.GETFIELD, "Target", "label", "I"); final Label dflt = new Label(); final Label state0 = new Label(); final Label state1 = new Label(); m.visitTableSwitchInsn(0, 1, dflt, state0, state1); m.visitLabel(state0); { m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKESTATIC, "kotlin/ResultKt", "throwOnFailure", "(Ljava/lang/Object;)V", false); range1.toInclusive = m.instructions.getLast(); } // line before "suspendingFunction" m.visitInsn(Opcodes.NOP); // line of "suspendingFunction" m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "", "suspendingFunction", "(Lkotlin/coroutines/Continuation;)Ljava/lang/Object;", false); m.visitInsn(Opcodes.DUP); final Range range2 = new Range(); range2.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ALOAD, 4); final Label continuationLabelAfterLoadedResult = new Label(); m.visitJumpInsn(Opcodes.IF_ACMPNE, continuationLabelAfterLoadedResult); // line of "runBlocking" m.visitVarInsn(Opcodes.ALOAD, 4); m.visitInsn(Opcodes.ARETURN); m.visitLabel(state1); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitFieldInsn(Opcodes.GETFIELD, "Target", "I$0", "I"); m.visitVarInsn(Opcodes.ISTORE, 3); { m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKESTATIC, "kotlin/ResultKt", "throwOnFailure", "(Ljava/lang/Object;)V", false); } m.visitVarInsn(Opcodes.ALOAD, 1); range2.toInclusive = m.instructions.getLast(); m.visitLabel(continuationLabelAfterLoadedResult); // line after "suspendingFunction" m.visitInsn(Opcodes.NOP); m.visitInsn(Opcodes.ARETURN); m.visitLabel(dflt); final Range range0 = new Range(); range0.fromInclusive = m.instructions.getLast(); m.visitTypeInsn(Opcodes.NEW, "java/lang/IllegalStateException"); m.visitInsn(Opcodes.DUP); m.visitLdcInsn("call to 'resume' before 'invoke' with coroutine"); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/IllegalStateException", "", "(Ljava/lang/String;)V", false); m.visitInsn(Opcodes.ATHROW); range0.toInclusive = m.instructions.getLast(); filter.filter(m, context, output); assertIgnored(range0, range1, range2); } /** *
	 *     runBlocking {
	 *         val x = 42
	 *         nop(x)
	 *         suspendingFunction()
	 *         nop(x)
	 *     }
	 * 
*/ @Test public void should_filter_suspending_lambdas() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "invokeSuspend", "(Ljava/lang/Object;)Ljava/lang/Object;", null, null); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); m.visitMethodInsn(Opcodes.INVOKESTATIC, "kotlin/coroutines/intrinsics/IntrinsicsKt", "getCOROUTINE_SUSPENDED", "()Ljava/lang/Object;", false); final Range range1 = new Range(); range1.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 4); m.visitVarInsn(Opcodes.ALOAD, 0); // line of "runBlocking" m.visitFieldInsn(Opcodes.GETFIELD, "Target", "label", "I"); final Label dflt = new Label(); final Label state0 = new Label(); final Label state1 = new Label(); m.visitTableSwitchInsn(0, 1, dflt, state0, state1); m.visitLabel(state0); { m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.DUP); m.visitTypeInsn(Opcodes.INSTANCEOF, "kotlin/Result$Failure"); Label label = new Label(); m.visitJumpInsn(Opcodes.IFEQ, label); m.visitTypeInsn(Opcodes.CHECKCAST, "kotlin/Result$Failure"); m.visitFieldInsn(Opcodes.GETFIELD, "kotlin/Result$Failure", "exception", "Ljava/lang/Throwable"); m.visitInsn(Opcodes.ATHROW); m.visitInsn(Opcodes.POP); range1.toInclusive = m.instructions.getLast(); m.visitLabel(label); } // line before "suspendingFunction" m.visitInsn(Opcodes.NOP); // line of "suspendingFunction" m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "", "suspendingFunction", "(Lkotlin/coroutines/Continuation;)Ljava/lang/Object;", false); m.visitInsn(Opcodes.DUP); final Range range2 = new Range(); range2.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ALOAD, 4); final Label continuationLabelAfterLoadedResult = new Label(); m.visitJumpInsn(Opcodes.IF_ACMPNE, continuationLabelAfterLoadedResult); // line of "runBlocking" m.visitVarInsn(Opcodes.ALOAD, 4); m.visitInsn(Opcodes.ARETURN); m.visitLabel(state1); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitFieldInsn(Opcodes.GETFIELD, "Target", "I$0", "I"); m.visitVarInsn(Opcodes.ISTORE, 3); { m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.DUP); m.visitTypeInsn(Opcodes.INSTANCEOF, "kotlin/Result$Failure"); final Label label = new Label(); m.visitJumpInsn(Opcodes.IFEQ, label); m.visitTypeInsn(Opcodes.CHECKCAST, "kotlin/Result$Failure"); m.visitFieldInsn(Opcodes.GETFIELD, "kotlin/Result$Failure", "exception", "Ljava/lang/Throwable"); m.visitInsn(Opcodes.ATHROW); m.visitInsn(Opcodes.POP); m.visitLabel(label); } m.visitVarInsn(Opcodes.ALOAD, 1); range2.toInclusive = m.instructions.getLast(); m.visitLabel(continuationLabelAfterLoadedResult); // line after "suspendingFunction" m.visitInsn(Opcodes.NOP); m.visitInsn(Opcodes.ARETURN); m.visitLabel(dflt); final Range range0 = new Range(); range0.fromInclusive = m.instructions.getLast(); m.visitTypeInsn(Opcodes.NEW, "java/lang/IllegalStateException"); m.visitInsn(Opcodes.DUP); m.visitLdcInsn("call to 'resume' before 'invoke' with coroutine"); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/IllegalStateException", "", "(Ljava/lang/String;)V", false); m.visitInsn(Opcodes.ATHROW); range0.toInclusive = m.instructions.getLast(); filter.filter(m, context, output); assertIgnored(range0, range1, range2); } /** *
	 *     suspend fun example() {
	 *         suspendingFunction()
	 *         nop()
	 *     }
	 * 
*/ @Test public void should_filter_suspending_functions() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_STATIC, "example", "(Lkotlin/coroutines/Continuation;)Ljava/lang/Object;", null, null); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); final int continuationArgumentIndex = 0; final int continuationIndex = 2; m.visitVarInsn(Opcodes.ALOAD, continuationArgumentIndex); final Range range1 = new Range(); range1.fromInclusive = m.instructions.getLast(); m.visitTypeInsn(Opcodes.INSTANCEOF, "ExampleKt$example$1"); final Label createStateInstance = new Label(); m.visitJumpInsn(Opcodes.IFEQ, createStateInstance); m.visitVarInsn(Opcodes.ALOAD, continuationArgumentIndex); m.visitTypeInsn(Opcodes.CHECKCAST, "ExampleKt$example$1"); m.visitVarInsn(Opcodes.ASTORE, continuationIndex); m.visitVarInsn(Opcodes.ALOAD, continuationIndex); m.visitFieldInsn(Opcodes.GETFIELD, "ExampleKt$example$1", "label", "I"); m.visitLdcInsn(Integer.valueOf(Integer.MIN_VALUE)); m.visitInsn(Opcodes.IAND); m.visitJumpInsn(Opcodes.IFEQ, createStateInstance); m.visitVarInsn(Opcodes.ALOAD, continuationIndex); m.visitInsn(Opcodes.DUP); m.visitFieldInsn(Opcodes.GETFIELD, "ExampleKt$example$1", "label", "I"); m.visitLdcInsn(Integer.valueOf(Integer.MIN_VALUE)); m.visitInsn(Opcodes.ISUB); m.visitFieldInsn(Opcodes.PUTFIELD, "ExampleKt$example$1", "label", "I"); final Label afterCoroutineStateCreated = new Label(); m.visitJumpInsn(Opcodes.GOTO, afterCoroutineStateCreated); m.visitLabel(createStateInstance); m.visitTypeInsn(Opcodes.NEW, "ExampleKt$example$1"); m.visitInsn(Opcodes.DUP); m.visitVarInsn(Opcodes.ALOAD, continuationArgumentIndex); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "ExampleKt$example$1", "", "(Lkotlin/coroutines/Continuation;)V", false); m.visitVarInsn(Opcodes.ASTORE, continuationIndex); m.visitLabel(afterCoroutineStateCreated); m.visitVarInsn(Opcodes.ALOAD, continuationIndex); m.visitFieldInsn(Opcodes.GETFIELD, "ExampleKt$example$1", "result", "Ljava/lang/Object;"); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitMethodInsn(Opcodes.INVOKESTATIC, "kotlin/coroutines/intrinsics/IntrinsicsKt", "getCOROUTINE_SUSPENDED", "()Ljava/lang/Object;", false); // line of "fun" m.visitVarInsn(Opcodes.ASTORE, 3); m.visitVarInsn(Opcodes.ALOAD, continuationIndex); m.visitFieldInsn(Opcodes.GETFIELD, "ExampleKt$example$1", "label", "I"); final Label dflt = new Label(); final Label state0 = new Label(); final Label state1 = new Label(); m.visitTableSwitchInsn(0, 1, dflt, state0, state1); m.visitLabel(state0); { m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.DUP); m.visitTypeInsn(Opcodes.INSTANCEOF, "kotlin/Result$Failure"); Label label = new Label(); m.visitJumpInsn(Opcodes.IFEQ, label); m.visitTypeInsn(Opcodes.CHECKCAST, "kotlin/Result$Failure"); m.visitFieldInsn(Opcodes.GETFIELD, "kotlin/Result$Failure", "exception", "Ljava/lang/Throwable"); m.visitInsn(Opcodes.ATHROW); m.visitInsn(Opcodes.POP); range1.toInclusive = m.instructions.getLast(); m.visitLabel(label); } // line of "suspendingFunction" m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "", "suspendingFunction", "(Lkotlin/coroutines/Continuation;)Ljava/lang/Object;", false); m.visitInsn(Opcodes.DUP); final Range range2 = new Range(); range2.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ALOAD, 3); final Label continuationLabelAfterLoadedResult = new Label(); m.visitJumpInsn(Opcodes.IF_ACMPNE, continuationLabelAfterLoadedResult); // line of "fun" m.visitVarInsn(Opcodes.ALOAD, 3); m.visitInsn(Opcodes.ARETURN); m.visitLabel(state1); { m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.DUP); m.visitTypeInsn(Opcodes.INSTANCEOF, "kotlin/Result$Failure"); final Label label = new Label(); m.visitJumpInsn(Opcodes.IFEQ, label); m.visitTypeInsn(Opcodes.CHECKCAST, "kotlin/Result$Failure"); m.visitFieldInsn(Opcodes.GETFIELD, "kotlin/Result$Failure", "exception", "Ljava/lang/Throwable"); m.visitInsn(Opcodes.ATHROW); m.visitInsn(Opcodes.POP); m.visitLabel(label); } m.visitVarInsn(Opcodes.ALOAD, 1); range2.toInclusive = m.instructions.getLast(); m.visitLabel(continuationLabelAfterLoadedResult); // line after "suspendingFunction" m.visitInsn(Opcodes.NOP); m.visitInsn(Opcodes.ARETURN); m.visitLabel(dflt); final Range range0 = new Range(); range0.fromInclusive = m.instructions.getLast(); m.visitTypeInsn(Opcodes.NEW, "java/lang/IllegalStateException"); m.visitInsn(Opcodes.DUP); m.visitLdcInsn("call to 'resume' before 'invoke' with coroutine"); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/IllegalStateException", "", "(Ljava/lang/String;)V", false); m.visitInsn(Opcodes.ATHROW); range0.toInclusive = m.instructions.getLast(); filter.filter(m, context, output); assertIgnored(range0, range1, range2); } /** *
	 *     suspend fun example(b: Boolean) {
	 *         if (b)
	 *             suspendingFunction()
	 *         else
	 *             suspendingFunction()
	 *     }
	 * 
*/ @Test public void should_filter_suspending_functions_with_tail_call_optimization() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "example", "(ZLkotlin/coroutines/Continuation;)Ljava/lang/Object;", null, null); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); final Label exit = new Label(); m.visitVarInsn(Opcodes.ILOAD, 1); final Label next = new Label(); m.visitJumpInsn(Opcodes.IFEQ, next); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "", "suspendingFunction", "(Lkotlin/coroutines/Continuation;)Ljava/lang/Object;", false); final Range range1 = new Range(); { m.visitInsn(Opcodes.DUP); range1.fromInclusive = m.instructions.getLast(); m.visitMethodInsn(Opcodes.INVOKESTATIC, "kotlin/coroutines/intrinsics/IntrinsicsKt", "getCOROUTINE_SUSPENDED", "()Ljava/lang/Object;", false); final Label label = new Label(); m.visitJumpInsn(Opcodes.IF_ACMPNE, label); m.visitInsn(Opcodes.ARETURN); m.visitLabel(label); m.visitInsn(Opcodes.POP); range1.toInclusive = m.instructions.getLast(); } m.visitJumpInsn(Opcodes.GOTO, exit); m.visitLabel(next); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "", "suspendingFunction", "(Lkotlin/coroutines/Continuation;)Ljava/lang/Object;", false); final Range range2 = new Range(); { m.visitInsn(Opcodes.DUP); range2.fromInclusive = m.instructions.getLast(); m.visitMethodInsn(Opcodes.INVOKESTATIC, "kotlin/coroutines/intrinsics/IntrinsicsKt", "getCOROUTINE_SUSPENDED", "()Ljava/lang/Object;", false); final Label label = new Label(); m.visitJumpInsn(Opcodes.IF_ACMPNE, label); m.visitInsn(Opcodes.ARETURN); m.visitLabel(label); m.visitInsn(Opcodes.POP); range2.toInclusive = m.instructions.getLast(); } m.visitLabel(exit); m.visitFieldInsn(Opcodes.GETSTATIC, "kotlin/Unit", "INSTANCE", "Lkotlin/Unit;"); m.visitInsn(Opcodes.ARETURN); filter.filter(m, context, output); assertIgnored(range1, range2); } } KotlinDefaultArgumentsFilterTest.java000066400000000000000000000146051451257705100367220ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit test for {@link KotlinDefaultArgumentsFilter}. */ public class KotlinDefaultArgumentsFilterTest extends FilterTestBase { private final IFilter filter = new KotlinDefaultArgumentsFilter(); private static MethodNode createMethod(final int access, final String name, final String descriptor) { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, access, name, descriptor, null, null); m.visitVarInsn(Opcodes.ILOAD, 2); m.visitInsn(Opcodes.ICONST_1); m.visitInsn(Opcodes.IAND); final Label label = new Label(); m.visitJumpInsn(Opcodes.IFEQ, label); // default argument m.visitLdcInsn(Integer.valueOf(42)); m.visitVarInsn(Opcodes.ISTORE, 1); m.visitLabel(label); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitVarInsn(Opcodes.ILOAD, 1); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "Target", "origin", "(I)V", false); m.visitInsn(Opcodes.RETURN); return m; } @Test public void should_filter() { final MethodNode m = createMethod(Opcodes.ACC_SYNTHETIC, "origin$default", "(LTarget;IILjava/lang/Object;)V"); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); filter.filter(m, context, output); assertIgnored(new Range(m.instructions.get(3), m.instructions.get(3))); } @Test public void should_not_filter_when_not_kotlin() { final MethodNode m = createMethod(Opcodes.ACC_SYNTHETIC, "not_kotlin_synthetic$default", "(LTarget;IILjava/lang/Object;)V"); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_when_suffix_absent() { final MethodNode m = createMethod(Opcodes.ACC_SYNTHETIC, "synthetic_without_suffix", "(LTarget;IILjava/lang/Object;)V"); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_when_not_synthetic() { final MethodNode m = createMethod(0, "not_synthetic$default", "(LTarget;IILjava/lang/Object;)V"); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); filter.filter(m, context, output); assertIgnored(); } /** *
	 * open class Open {
	 *     open fun foo(a: Int = 42) {
	 *     }
	 * }
	 * 
*/ @Test public void should_filter_open_functions() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_SYNTHETIC, "foo$default", "(LOpen;IILjava/lang/Object;)V", null, null); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); { m.visitVarInsn(Opcodes.ALOAD, 3); final Label label = new Label(); m.visitJumpInsn(Opcodes.IFNULL, label); m.visitTypeInsn(Opcodes.NEW, "java/lang/UnsupportedOperationException"); m.visitInsn(Opcodes.DUP); m.visitLdcInsn( "Super calls with default arguments not supported in this target, function: foo"); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/UnsupportedOperationException", "", "(Ljava/lang/String;)V", false); m.visitInsn(Opcodes.ATHROW); m.visitLabel(label); } { m.visitVarInsn(Opcodes.ILOAD, 2); m.visitInsn(Opcodes.ICONST_1); m.visitInsn(Opcodes.IAND); final Label label = new Label(); m.visitJumpInsn(Opcodes.IFEQ, label); // default argument m.visitLdcInsn(Integer.valueOf(42)); m.visitVarInsn(Opcodes.ISTORE, 1); m.visitLabel(label); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitVarInsn(Opcodes.ILOAD, 1); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "Open", "foo", "(I)V", false); m.visitInsn(Opcodes.RETURN); } filter.filter(m, context, output); assertIgnored( new Range(m.instructions.getFirst(), m.instructions.get(6)), new Range(m.instructions.get(11), m.instructions.get(11))); } /** *
	 * class C(a: Int = 42)
	 * 
*/ @Test public void should_filter_constructors() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_SYNTHETIC, "", "(IILkotlin/jvm/internal/DefaultConstructorMarker;)V", null, null); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); m.visitVarInsn(Opcodes.ILOAD, 2); m.visitInsn(Opcodes.ICONST_1); m.visitInsn(Opcodes.IAND); Label label = new Label(); m.visitJumpInsn(Opcodes.IFEQ, label); // default argument m.visitLdcInsn(Integer.valueOf(42)); m.visitVarInsn(Opcodes.ISTORE, 1); m.visitLabel(label); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitVarInsn(Opcodes.ILOAD, 1); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "Owner", "", "(I)V", false); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(new Range(m.instructions.get(3), m.instructions.get(3))); } /** *
	 * data class C(val x: Long = 42)
	 * 
*/ @Test public void should_filter_methods_with_parameters_that_consume_two_slots() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_SYNTHETIC, "", "(JILkotlin/jvm/internal/DefaultConstructorMarker;)V", null, null); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); m.visitVarInsn(Opcodes.ILOAD, 3); m.visitInsn(Opcodes.ICONST_1); m.visitInsn(Opcodes.IAND); final Label label = new Label(); m.visitJumpInsn(Opcodes.IFEQ, label); // default argument m.visitLdcInsn(Integer.valueOf(42)); m.visitVarInsn(Opcodes.ISTORE, 1); m.visitLabel(label); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitVarInsn(Opcodes.ILOAD, 1); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "Owner", "", "(J)V", false); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(new Range(m.instructions.get(3), m.instructions.get(3))); } } KotlinDefaultMethodsFilterTest.java000066400000000000000000000050441451257705100363550ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit test for {@link KotlinDefaultMethodsFilter}. */ public class KotlinDefaultMethodsFilterTest extends FilterTestBase { private final IFilter filter = new KotlinDefaultMethodsFilter(); @Test public void should_filter() { context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "m", "()V", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Target$DefaultImpls", "m", "(LTarget;)V", false); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_not_filter_when_invokestatic_owner_does_not_match() { context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "m", "()V", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Target", "m", "(LTarget;)V", false); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_when_instructions_do_not_match() { context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "m", "()V", null, null); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_when_not_kotlin() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "m", "()V", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Target$DefaultImpls", "m", "(LTarget;)V", false); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(); } } KotlinGeneratedFilterTest.java000066400000000000000000000055451451257705100353510ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Nikolay Krasko - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link KotlinGeneratedFilter}. */ public class KotlinGeneratedFilterTest extends FilterTestBase { private final IFilter filter = new KotlinGeneratedFilter(); @Test public void testNoLinesForKotlinWithDebug() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()I", null, null); m.visitInsn(Opcodes.ICONST_0); m.visitInsn(Opcodes.IRETURN); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void testWithLinesForKotlinWithDebug() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()I", null, null); m.visitAnnotation("Lother/Annotation;", false); m.visitLineNumber(12, new Label()); m.visitInsn(Opcodes.ICONST_0); m.visitInsn(Opcodes.IRETURN); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); filter.filter(m, context, output); assertIgnored(); } @Test public void testNoLinesNonKotlinWithDebug() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()I", null, null); m.visitInsn(Opcodes.ICONST_0); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertIgnored(); } @Test public void testNoLinesForKotlinNoDebug() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()I", null, null); m.visitInsn(Opcodes.ICONST_0); m.visitInsn(Opcodes.IRETURN); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); context.sourceFileName = null; filter.filter(m, context, output); assertIgnored(); } @Test public void testWithLinesForKotlinNoDebug() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()I", null, null); m.visitInsn(Opcodes.ICONST_0); m.visitInsn(Opcodes.IRETURN); m.visitLineNumber(12, new Label()); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); context.sourceFileName = null; filter.filter(m, context, output); assertIgnored(); } } KotlinInlineFilterTest.java000066400000000000000000000222521451257705100346630ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import static org.junit.Assert.assertEquals; import static org.junit.Assert.fail; import java.util.ArrayList; import java.util.List; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link KotlinInlineFilter}. */ public class KotlinInlineFilterTest extends FilterTestBase { private final KotlinInlineFilter filter = new KotlinInlineFilter(); private final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "callsite", "()V", null, null); @Test public void should_filter() { context.sourceFileName = "callsite.kt"; context.sourceDebugExtension = "" // + "SMAP\n" // + "callsite.kt\n" // OutputFileName=callsite.kt + "Kotlin\n" // DefaultStratumId=Kotlin + "*S Kotlin\n" // StratumID=Kotlin + "*F\n" // FileSection + "+ 1 callsite.kt\n" // FileID=1,FileName=callsite.kt + "CallsiteKt\n" // + "+ 2 a.kt\n" // FileID=2,FileName=a.kt + "AKt\n" // + "+ 3 b.kt\n" // FileID=3,FileName=b.kt + "BKt\n" // + "*L\n" // LineSection + "1#1,8:1\n" // InputStartLine=1,LineFileID=1,RepeatCount=8,OutputStartLine=1 + "2#2,2:9\n" // InputStartLine=2,LineFileID=2,RepeatCount=2,OutputStartLine=9 + "2#3,2:11\n" // InputStartLine=2,LineFileID=3,RepeatCount=2,OutputStartLine=11 + "*E\n"; // EndSection context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); m.visitLineNumber(2, new Label()); m.visitInsn(Opcodes.NOP); m.visitLineNumber(9, new Label()); shouldIgnorePrevious(m); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Stubs", "nop", "()V", false); shouldIgnorePrevious(m); m.visitLineNumber(10, new Label()); shouldIgnorePrevious(m); m.visitInsn(Opcodes.NOP); shouldIgnorePrevious(m); m.visitLineNumber(3, new Label()); m.visitInsn(Opcodes.NOP); m.visitLineNumber(11, new Label()); shouldIgnorePrevious(m); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Stubs", "nop", "()V", false); shouldIgnorePrevious(m); m.visitLineNumber(12, new Label()); shouldIgnorePrevious(m); m.visitInsn(Opcodes.NOP); shouldIgnorePrevious(m); m.visitLineNumber(4, new Label()); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(expectedRanges.toArray(new Range[0])); // should not reparse: context.sourceDebugExtension = ""; filter.filter(m, context, output); } /** *
	 *     inline fun inlined_top_level() {
	 *       Stubs.nop()
	 *     }
	 *
	 *     class Callsite {
	 *       fun inlined() {
	 *           Stubs.nop()
	 *       }
	 *
	 *       fun callsite {
	 *         inlined_top_level()
	 *         inlined()
	 *       }
	 *     }
	 * 
*/ @Test public void should_filter_when_in_same_file() { context.sourceFileName = "example.kt"; context.sourceDebugExtension = "" // + "SMAP\n" // + "example.kt\n" // OutputFileName=example.kt + "Kotlin\n" // DefaultStratumId=Kotlin + "*S Kotlin\n" // StratumID=Kotlin + "*F\n" // FileSection + "+ 1 example.kt\n" // FileID=1,FileName=example.kt + "Callsite\n" // + "+ 2 example.kt\n" // FileID=2,FileName=example.kt + "ExampleKt\n" // + "*L\n" // LineSection + "1#1,15:1\n" // InputStartLine=1,LineFileID=1,RepeatCount=10,OutputStartLine=1 + "7#1,2:18\n" // InputStartLine=7,LineFileID=1,RepeatCount=2,OutputStartLine=18 + "2#2,2:16\n" // InputStartLine=2,LineFileID=2,RepeatCount=2,OutputStartLine=16 + "*E\n"; // EndSection context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); m.visitLineNumber(11, new Label()); m.visitInsn(Opcodes.NOP); m.visitLineNumber(16, new Label()); shouldIgnorePrevious(m); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Stubs", "nop", "()V", false); shouldIgnorePrevious(m); m.visitLineNumber(17, new Label()); shouldIgnorePrevious(m); m.visitInsn(Opcodes.NOP); shouldIgnorePrevious(m); m.visitLineNumber(12, new Label()); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitLineNumber(18, new Label()); shouldIgnorePrevious(m); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Stubs", "nop", "()V", false); shouldIgnorePrevious(m); m.visitLineNumber(19, new Label()); shouldIgnorePrevious(m); m.visitInsn(Opcodes.NOP); shouldIgnorePrevious(m); m.visitLineNumber(13, new Label()); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(expectedRanges.toArray(new Range[0])); } /** * See KT-37704 * *
	 * inline fun f() {}
	 * fun g() = f()
	 * 
*/ @Test public void should_filter_without_parsing_KotlinDebug_stratum() { context.sourceFileName = "Example.kt"; context.sourceDebugExtension = "" // + "SMAP\n" // + "Example.kt\n" // OutputFileName=Example.kt + "Kotlin\n" // DefaultStratumId=Kotlin + "*S Kotlin\n" // StratumID=Kotlin + "*F\n" // FileSection + "+ 1 Example.kt\n" // FileID=1,FileName=Example.kt + "ExampleKt\n" // + "*L\n" // LineSection + "1#1,3:1\n" // InputStartLine=1,LineFileID=1,RepeatCount=3,OutputStartLine=1 + "1#1:4\n" // InputStartLine=1,LineFileID=1,OutputStartLine=4 + "*S KotlinDebug\n"; // StratumID=KotlinDebug context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); m.visitLineNumber(2, new Label()); m.visitInsn(Opcodes.ICONST_0); m.visitVarInsn(Opcodes.ISTORE, 0); m.visitLineNumber(4, new Label()); shouldIgnorePrevious(m); m.visitInsn(Opcodes.NOP); shouldIgnorePrevious(m); m.visitLineNumber(3, new Label()); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(expectedRanges.toArray(new Range[0])); } @Test public void should_not_parse_SourceDebugExtension_attribute_when_no_kotlin_metadata_annotation() { context.sourceDebugExtension = "SMAP"; m.visitLineNumber(1, new Label()); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_when_no_SourceDebugExtension_attribute() { context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); m.visitLineNumber(1, new Label()); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(); } @Test public void should_throw_exception_when_SMAP_incomplete() { context.sourceDebugExtension = "" // + "SMAP\n"; context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); try { filter.filter(m, context, output); fail("exception expected"); } catch (final IllegalStateException e) { assertEquals("Unexpected SMAP line: null", e.getMessage()); } } @Test public void should_throw_exception_when_unexpected_FileInfo() { context.sourceFileName = "callsite.kt"; context.sourceDebugExtension = "" // + "SMAP\n" // + "callsite.kt\n" // + "Kotlin\n" // + "*S Kotlin\n" // + "*F\n" // + "xxx"; context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); try { filter.filter(m, context, output); fail("exception expected"); } catch (final IllegalStateException e) { assertEquals("Unexpected SMAP line: xxx", e.getMessage()); } } @Test public void should_throw_exception_when_no_SourceFileId_for_SourceFile() { context.sourceFileName = "example.kt"; context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); context.sourceDebugExtension = "" // + "SMAP\n" // + "example.kt\n" // + "Kotlin\n" // + "*S Kotlin\n" // + "*F\n" // + "+ 1 another.kt\n" // + "AnotherKt\n" // + "*L\n" // + "*E\n"; try { filter.filter(m, context, output); fail("exception expected"); } catch (final IllegalStateException e) { assertEquals("Unexpected SMAP FileSection", e.getMessage()); } } @Test public void should_throw_exception_when_unexpected_LineInfo() { context.sourceFileName = "callsite.kt"; context.sourceDebugExtension = "" // + "SMAP\n" // + "callsite.kt\n" // + "Kotlin\n" // + "*S Kotlin\n" // + "*F\n" // + "+ 1 callsite.kt\n" // + "Callsite\n" // + "*L\n" // + "xxx"; context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); try { filter.filter(m, context, output); fail("exception expected"); } catch (final IllegalStateException e) { assertEquals("Unexpected SMAP line: xxx", e.getMessage()); } } private final List expectedRanges = new ArrayList(); private void shouldIgnorePrevious(final MethodNode m) { expectedRanges.add( new Range(m.instructions.getLast(), m.instructions.getLast())); } } KotlinLateinitFilterTest.java000066400000000000000000000061701451257705100352170ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Fabian Mastenbroek - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link KotlinLateinitFilter}. */ public class KotlinLateinitFilterTest extends FilterTestBase { private final KotlinLateinitFilter filter = new KotlinLateinitFilter(); private final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "()V", null, null); @Test public void testLateinitBranchIsFiltered() { final Label l1 = new Label(); final Label l2 = new Label(); m.visitLabel(l1); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitFieldInsn(Opcodes.GETFIELD, "com/better/alarm/background/VibrationService", "wakeLock", "Landroid/os/PowerManager$WakeLock;"); m.visitInsn(Opcodes.DUP); m.visitJumpInsn(Opcodes.IFNONNULL, l2); final AbstractInsnNode expectedFrom = m.instructions.getLast(); m.visitLdcInsn("wakelock"); m.visitMethodInsn(Opcodes.INVOKESTATIC, "kotlin/jvm/internal/Intrinsics", "throwUninitializedPropertyAccessException", "(Ljava/lang/String;)V", false); final AbstractInsnNode expectedTo = m.instructions.getLast(); m.visitLabel(l2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "android/os/PowerManager$WakeLock", "acquire", "", false); filter.filter(m, context, output); assertIgnored(new Range(expectedFrom, expectedTo)); } /** *
	 * class Example {
	 *   private lateinit var x: String
	 *   fun example() = x
	 * }
	 * 
*/ @Test public void should_filter_Kotlin_1_5() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "example", "()Ljava/lang/String;", null, null); Label label = new Label(); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitFieldInsn(Opcodes.GETFIELD, "Example", "x", "Ljava/lang/String;"); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitJumpInsn(Opcodes.IFNONNULL, label); final AbstractInsnNode expectedFrom = m.instructions.getLast(); m.visitLdcInsn("x"); m.visitMethodInsn(Opcodes.INVOKESTATIC, "kotlin/jvm/internal/Intrinsics", "throwUninitializedPropertyAccessException", "(Ljava/lang/String;)V", false); m.visitInsn(Opcodes.ACONST_NULL); m.visitInsn(Opcodes.ATHROW); final AbstractInsnNode expectedTo = m.instructions.getLast(); m.visitLabel(label); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.ARETURN); filter.filter(m, context, output); assertIgnored(new Range(expectedFrom, expectedTo)); } } KotlinNotNullOperatorFilterTest.java000066400000000000000000000034661451257705100365620ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link KotlinNotNullOperatorFilter}. */ public class KotlinNotNullOperatorFilterTest extends FilterTestBase { private final KotlinNotNullOperatorFilter filter = new KotlinNotNullOperatorFilter(); private final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "example", "()V", null, null); /** *
	 *     return x!!.length
	 * 
*/ @Test public void should_filter() { m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.DUP); final Range range = new Range(); final Label label = new Label(); m.visitJumpInsn(Opcodes.IFNONNULL, label); range.fromInclusive = m.instructions.getLast(); // no line number here and hence no probe m.visitMethodInsn(Opcodes.INVOKESTATIC, "kotlin/jvm/internal/Intrinsics", "throwNpe", "()V", false); range.toInclusive = m.instructions.getLast(); m.visitLabel(label); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "length", "()I", false); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertIgnored(range); } } KotlinUnsafeCastOperatorFilterTest.java000066400000000000000000000126341451257705100372200ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link KotlinUnsafeCastOperatorFilter}. */ public class KotlinUnsafeCastOperatorFilterTest extends FilterTestBase { private final KotlinUnsafeCastOperatorFilter filter = new KotlinUnsafeCastOperatorFilter(); private final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "()V", null, null); @Test public void should_filter() { context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); final Label label = new Label(); m.visitInsn(Opcodes.DUP); m.visitJumpInsn(Opcodes.IFNONNULL, label); final AbstractInsnNode expectedFrom = m.instructions.getLast(); m.visitTypeInsn(Opcodes.NEW, "kotlin/TypeCastException"); m.visitInsn(Opcodes.DUP); m.visitLdcInsn("null cannot be cast to non-null type kotlin.String"); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "kotlin/TypeCastException", "", "(Ljava/lang/String;)V", false); m.visitInsn(Opcodes.ATHROW); final AbstractInsnNode expectedTo = m.instructions.getLast(); m.visitLabel(label); filter.filter(m, context, output); assertIgnored(new Range(expectedFrom, expectedTo)); } @Test public void should_filter_Kotlin_1_4() { context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); final Label label = new Label(); m.visitInsn(Opcodes.DUP); m.visitJumpInsn(Opcodes.IFNONNULL, label); final AbstractInsnNode expectedFrom = m.instructions.getLast(); m.visitTypeInsn(Opcodes.NEW, "java/lang/NullPointerException"); m.visitInsn(Opcodes.DUP); m.visitLdcInsn("null cannot be cast to non-null type kotlin.String"); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/NullPointerException", "", "(Ljava/lang/String;)V", false); m.visitInsn(Opcodes.ATHROW); final AbstractInsnNode expectedTo = m.instructions.getLast(); m.visitLabel(label); filter.filter(m, context, output); assertIgnored(new Range(expectedFrom, expectedTo)); } /** * For * *
	 *   fun f(s: String?): String {
	 * 	   return s as String
	 *   }
	 * 
* * bytecode generated by Kotlin compiler version 1.4 is different from * bytecode generated by version 1.5, unfortunately bytecode generated by * later is the same as bytecode that both versions generate for * *
	 *   fun f(s: String?): String {
	 *     if (s == null)
	 *       throw NullPointerException("null cannot be cast to non-null type kotlin.String")
	 *     return s
	 *   }
	 * 
*/ @Test public void should_filter_Kotlin_1_5() { context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); final Label label = new Label(); m.visitJumpInsn(Opcodes.IFNONNULL, label); final AbstractInsnNode expectedFrom = m.instructions.getLast(); m.visitTypeInsn(Opcodes.NEW, "java/lang/NullPointerException"); m.visitInsn(Opcodes.DUP); m.visitLdcInsn("null cannot be cast to non-null type kotlin.String"); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/NullPointerException", "", "(Ljava/lang/String;)V", false); m.visitInsn(Opcodes.ATHROW); final AbstractInsnNode expectedTo = m.instructions.getLast(); m.visitLabel(label); m.visitVarInsn(Opcodes.ALOAD, 0); filter.filter(m, context, output); assertIgnored(new Range(expectedFrom, expectedTo)); } @Test public void should_filter_Kotlin_1_6() { context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); final Label label = new Label(); m.visitInsn(Opcodes.DUP); m.visitJumpInsn(Opcodes.IFNONNULL, label); final AbstractInsnNode expectedFrom = m.instructions.getLast(); m.visitInsn(Opcodes.POP); m.visitTypeInsn(Opcodes.NEW, "java/lang/NullPointerException"); m.visitInsn(Opcodes.DUP); m.visitLdcInsn("null cannot be cast to non-null type kotlin.String"); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/NullPointerException", "", "(Ljava/lang/String;)V", false); m.visitInsn(Opcodes.ATHROW); final AbstractInsnNode expectedTo = m.instructions.getLast(); m.visitLabel(label); filter.filter(m, context, output); assertIgnored(new Range(expectedFrom, expectedTo)); } @Test public void should_not_filter_when_not_kotlin() { m.visitInsn(Opcodes.DUP); final Label label = new Label(); m.visitJumpInsn(Opcodes.IFNONNULL, label); m.visitTypeInsn(Opcodes.NEW, "java/lang/NullPointerException"); m.visitInsn(Opcodes.DUP); m.visitLdcInsn("null cannot be cast to non-null type kotlin.String"); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/NullPointerException", "", "(Ljava/lang/String;)V", false); m.visitInsn(Opcodes.ATHROW); m.visitLabel(label); filter.filter(m, context, output); assertIgnored(); } } KotlinWhenFilterTest.java000066400000000000000000000071311451257705100343450ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import java.util.HashSet; import java.util.Set; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link KotlinWhenFilter}. */ public class KotlinWhenFilterTest extends FilterTestBase { private final KotlinWhenFilter filter = new KotlinWhenFilter(); private final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "()V", null, null); @Test public void should_filter_implicit_else() { final Label label = new Label(); final Range range1 = new Range(); m.visitInsn(Opcodes.NOP); m.visitJumpInsn(Opcodes.IFEQ, label); range1.fromInclusive = m.instructions.getLast(); range1.toInclusive = m.instructions.getLast(); m.visitInsn(Opcodes.NOP); final Range range2 = new Range(); m.visitLabel(label); range2.fromInclusive = m.instructions.getLast(); m.visitTypeInsn(Opcodes.NEW, "kotlin/NoWhenBranchMatchedException"); m.visitInsn(Opcodes.DUP); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "kotlin/NoWhenBranchMatchedException", "", "()V", false); m.visitInsn(Opcodes.ATHROW); range2.toInclusive = m.instructions.getLast(); filter.filter(m, context, output); assertIgnored(range1, range2); assertNoReplacedBranches(); } @Test public void should_not_filter_explicit_else() { final Label label = new Label(); m.visitInsn(Opcodes.NOP); m.visitJumpInsn(Opcodes.IFEQ, label); m.visitInsn(Opcodes.NOP); m.visitLabel(label); m.visitTypeInsn(Opcodes.NEW, "kotlin/NoWhenBranchMatchedException"); m.visitInsn(Opcodes.DUP); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "kotlin/NoWhenBranchMatchedException", "", "()V", false); m.visitTypeInsn(Opcodes.CHECKCAST, "java/lang/Throwable"); m.visitInsn(Opcodes.ATHROW); filter.filter(m, context, output); assertIgnored(); assertNoReplacedBranches(); } @Test public void should_filter_implicit_default() { final Label case1 = new Label(); final Label caseDefault = new Label(); final Label after = new Label(); m.visitInsn(Opcodes.NOP); m.visitTableSwitchInsn(0, 0, caseDefault, case1); final AbstractInsnNode switchNode = m.instructions.getLast(); final Set newTargets = new HashSet(); m.visitLabel(case1); m.visitInsn(Opcodes.ICONST_1); newTargets.add(m.instructions.getLast()); m.visitJumpInsn(Opcodes.GOTO, after); final Range range1 = new Range(); m.visitLabel(caseDefault); range1.fromInclusive = m.instructions.getLast(); m.visitTypeInsn(Opcodes.NEW, "kotlin/NoWhenBranchMatchedException"); m.visitInsn(Opcodes.DUP); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "kotlin/NoWhenBranchMatchedException", "", "()V", false); m.visitInsn(Opcodes.ATHROW); range1.toInclusive = m.instructions.getLast(); m.visitLabel(after); filter.filter(m, context, output); assertIgnored(range1); assertReplacedBranches(switchNode, newTargets); } } KotlinWhenStringFilterTest.java000066400000000000000000000146661451257705100355470ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import java.util.HashSet; import java.util.Set; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link KotlinWhenStringFilter}. */ public class KotlinWhenStringFilterTest extends FilterTestBase { private final IFilter filter = new KotlinWhenStringFilter(); @Test public void should_filter() { final Set expectedNewTargets = new HashSet(); final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "()V", null, null); final Label h1 = new Label(); final Label sameHash = new Label(); final Label h2 = new Label(); final Label case1 = new Label(); final Label case2 = new Label(); final Label case3 = new Label(); final Label defaultCase = new Label(); // filter should not remember this unrelated slot m.visitLdcInsn(""); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitVarInsn(Opcodes.ALOAD, 1); // switch (...) m.visitVarInsn(Opcodes.ASTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "hashCode", "()I", false); m.visitTableSwitchInsn(97, 98, defaultCase, h1, h2); // case "a" m.visitLabel(h1); final AbstractInsnNode expectedFromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitLdcInsn("a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); m.visitJumpInsn(Opcodes.IFEQ, sameHash); m.visitJumpInsn(Opcodes.GOTO, case1); // case "\u0000a" m.visitLabel(sameHash); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitLdcInsn("\u0000a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); m.visitJumpInsn(Opcodes.IFEQ, defaultCase); m.visitJumpInsn(Opcodes.GOTO, case2); // case "b" m.visitLabel(h2); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitLdcInsn("\u0000a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); m.visitJumpInsn(Opcodes.IFEQ, defaultCase); m.visitJumpInsn(Opcodes.GOTO, case3); final AbstractInsnNode expectedToInclusive = m.instructions.getLast(); m.visitLabel(case1); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(case2); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(case3); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(defaultCase); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); filter.filter(m, context, output); assertReplacedBranches(expectedFromInclusive.getPrevious(), expectedNewTargets); assertIgnored(new Range(expectedFromInclusive, expectedToInclusive)); } /** *
	 * fun example(p: String) {
	 *   when (p) {
	 *     "b" -> return
	 *     "a" -> return
	 *     "\u0000a" -> return
	 *   }
	 * }
	 * 
*/ @Test public void should_filter_when_biggest_hashCode_first() { final Set expectedNewTargets = new HashSet(); final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "example", "(Ljava/lang/String;)V", null, null); final Label h1 = new Label(); final Label sameHash = new Label(); final Label h2 = new Label(); final Label case1 = new Label(); final Label case2 = new Label(); final Label case3 = new Label(); final Label defaultCase = new Label(); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "hashCode", "()I", false); m.visitTableSwitchInsn(97, 98, defaultCase, h1, h2); m.visitLabel(h1); final AbstractInsnNode expectedFromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitLdcInsn("a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); m.visitJumpInsn(Opcodes.IFEQ, sameHash); m.visitJumpInsn(Opcodes.GOTO, case2); m.visitLabel(sameHash); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitLdcInsn("\u0000a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); m.visitJumpInsn(Opcodes.IFEQ, defaultCase); m.visitJumpInsn(Opcodes.GOTO, case3); m.visitLabel(h2); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitLdcInsn("b"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); m.visitJumpInsn(Opcodes.IFEQ, defaultCase); final AbstractInsnNode expectedToInclusive = m.instructions.getLast(); m.visitLabel(case1); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(case2); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(case3); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(defaultCase); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); filter.filter(m, context, output); assertIgnored(new Range(expectedFromInclusive, expectedToInclusive)); assertReplacedBranches(expectedFromInclusive.getPrevious(), expectedNewTargets); } @Test public void should_not_filter_empty_lookup_switch() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "(Ljava/lang/String;)V", null, null); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "hashCode", "()I", false); final Label defaultCase = new Label(); m.visitLookupSwitchInsn(defaultCase, null, new Label[] {}); m.visitLabel(defaultCase); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(); } } PrivateEmptyNoArgConstructorFilterTest.java000066400000000000000000000025001451257705100401040ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link PrivateEmptyNoArgConstructorFilter}. */ public class PrivateEmptyNoArgConstructorFilterTest extends FilterTestBase { private final IFilter filter = new PrivateEmptyNoArgConstructorFilter(); @Test public void test() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_PRIVATE, "", "()V", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/Object", "", "()V", false); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertMethodIgnored(m); } } RecordPatternFilterTest.java000066400000000000000000000157611451257705100350470ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Handle; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.Type; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link RecordPatternFilter}. */ public class RecordPatternFilterTest extends FilterTestBase { private final IFilter filter = new RecordPatternFilter(); /** *
	 *   record Point(int x, int y) {}
	 *
	 *   void example(Object o) {
	 *     if (o instanceof Point(int x, int y)) {
	 *       ...
	 *     }
	 *   }
	 * 
*/ @Test public void should_filter_instanceof() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "example", "()V", null, null); final Label start1 = new Label(); final Label end1 = new Label(); final Label handler = new Label(); m.visitTryCatchBlock(start1, end1, handler, "java/lang/Throwable"); final Label start2 = new Label(); final Label end2 = new Label(); m.visitTryCatchBlock(start2, end2, handler, "java/lang/Throwable"); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitTypeInsn(Opcodes.INSTANCEOF, "Example$Point"); final Label label1 = new Label(); m.visitJumpInsn(Opcodes.IFEQ, label1); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitTypeInsn(Opcodes.CHECKCAST, "Example$Point"); m.visitVarInsn(Opcodes.ASTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitLabel(start1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Example$Point", "x", "()I", false); m.visitLabel(end1); m.visitVarInsn(Opcodes.ISTORE, 5); m.visitVarInsn(Opcodes.ILOAD, 5); m.visitVarInsn(Opcodes.ISTORE, 3); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitLabel(start2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Example$Point", "y", "()I", false); m.visitLabel(end2); m.visitVarInsn(Opcodes.ISTORE, 5); m.visitVarInsn(Opcodes.ILOAD, 5); m.visitVarInsn(Opcodes.ISTORE, 4); m.visitVarInsn(Opcodes.ILOAD, 3); m.visitVarInsn(Opcodes.ILOAD, 4); m.visitInsn(Opcodes.IADD); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Example", "nop", "(I)V", false); m.visitLabel(label1); final Label label2 = new Label(); m.visitJumpInsn(Opcodes.GOTO, label2); m.visitLabel(handler); final Range range = new Range(); range.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitTypeInsn(Opcodes.NEW, "java/lang/MatchException"); m.visitInsn(Opcodes.DUP); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "toString", "()Ljava/lang/String;", false); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/MatchException", "", "(Ljava/lang/String;Ljava/lang/Throwable;)V", false); m.visitInsn(Opcodes.ATHROW); range.toInclusive = m.instructions.getLast(); m.visitLabel(label2); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(range, range); } /** *
	 *   record Point(int x, int y) {}
	 *
	 *   void example(Object o) {
	 *     switch (o) {
	 *       case Point(int x, int y) -> ...
	 *       default -> ...
	 *     }
	 *   }
	 * 
*/ @Test public void should_filter_switch() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "example", "()V", null, null); final Label start1 = new Label(); final Label end1 = new Label(); final Label handler = new Label(); m.visitTryCatchBlock(start1, end1, handler, "java/lang/Throwable"); final Label start2 = new Label(); final Label end2 = new Label(); m.visitTryCatchBlock(start2, end2, handler, "java/lang/Throwable"); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.DUP); m.visitMethodInsn(Opcodes.INVOKESTATIC, "java/util/Objects", "requireNonNull", "(Ljava/lang/Object;)Ljava/lang/Object;", false); m.visitInsn(Opcodes.POP); m.visitVarInsn(Opcodes.ASTORE, 2); m.visitInsn(Opcodes.ICONST_0); m.visitVarInsn(Opcodes.ISTORE, 3); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ILOAD, 3); m.visitInvokeDynamicInsn("typeSwitch", "(Ljava/lang/Object;I)I", new Handle(Opcodes.H_INVOKESTATIC, "java/lang/runtime/SwitchBootstraps", "typeSwitch", "(Ljava/lang/invoke/MethodHandles$Lookup;Ljava/lang/String;Ljava/lang/invoke/MethodType;[Ljava/lang/Object;)Ljava/lang/invoke/CallSite;", false), new Object[] { Type.getType("LExample$Point;") }); final Label case1 = new Label(); final Label dflt = new Label(); m.visitLookupSwitchInsn(dflt, new int[] { 0 }, new Label[] { case1 }); m.visitLabel(case1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitTypeInsn(Opcodes.CHECKCAST, "Example$Point"); m.visitVarInsn(Opcodes.ASTORE, 4); m.visitVarInsn(Opcodes.ALOAD, 4); m.visitLabel(start1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Example$Point", "x", "()I", false); m.visitLabel(end1); m.visitVarInsn(Opcodes.ISTORE, 7); m.visitVarInsn(Opcodes.ILOAD, 7); m.visitVarInsn(Opcodes.ISTORE, 5); m.visitVarInsn(Opcodes.ALOAD, 4); m.visitLabel(start2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Example$Point", "y", "()I", false); m.visitLabel(end2); m.visitVarInsn(Opcodes.ISTORE, 7); m.visitVarInsn(Opcodes.ILOAD, 7); m.visitVarInsn(Opcodes.ISTORE, 6); m.visitVarInsn(Opcodes.ILOAD, 5); m.visitVarInsn(Opcodes.ILOAD, 6); m.visitInsn(Opcodes.IADD); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Example", "nop", "(I)V", false); final Label label1 = new Label(); m.visitJumpInsn(Opcodes.GOTO, label1); m.visitLabel(dflt); m.visitInsn(Opcodes.ICONST_0); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Example", "nop", "(I)V", false); m.visitLabel(label1); final Label label2 = new Label(); m.visitJumpInsn(Opcodes.GOTO, label2); m.visitLabel(handler); final Range range = new Range(); range.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitTypeInsn(Opcodes.NEW, "java/lang/MatchException"); m.visitInsn(Opcodes.DUP); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "toString", "()Ljava/lang/String;", false); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/MatchException", "", "(Ljava/lang/String;Ljava/lang/Throwable;)V", false); m.visitInsn(Opcodes.ATHROW); range.toInclusive = m.instructions.getLast(); m.visitLabel(label2); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(range, range); } } RecordsFilterTest.java000066400000000000000000000174621451257705100336740ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Handle; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link RecordsFilter}. */ public class RecordsFilterTest extends FilterTestBase { private final RecordsFilter filter = new RecordsFilter(); @Test public void should_filter_generated_toString_method() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "toString", "()Ljava/lang/String;", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitInvokeDynamicInsn("toString", "(LPoint;)Ljava/lang/String;", new Handle(Opcodes.H_INVOKESTATIC, "java/lang/runtime/ObjectMethods", "bootstrap", "(Ljava/lang/invoke/MethodHandles$Lookup;Ljava/lang/String;Ljava/lang/invoke/TypeDescriptor;Ljava/lang/Class;Ljava/lang/String;[Ljava/lang/invoke/MethodHandle;)Ljava/lang/Object;", false)); m.visitInsn(Opcodes.ARETURN); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_not_filter_custom_toString_method() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "toString", "()Ljava/lang/String;", null, null); m.visitLdcInsn(""); m.visitInsn(Opcodes.ARETURN); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_non_toString_method() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "toString", "()V", null, null); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(); } @Test public void should_filter_generated_hashCode_method() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()I", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitInvokeDynamicInsn("hashCode", "(LPoint;)I", new Handle( Opcodes.H_INVOKESTATIC, "java/lang/runtime/ObjectMethods", "bootstrap", "(Ljava/lang/invoke/MethodHandles$Lookup;Ljava/lang/String;Ljava/lang/invoke/TypeDescriptor;Ljava/lang/Class;Ljava/lang/String;[Ljava/lang/invoke/MethodHandle;)Ljava/lang/Object;", false)); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_not_filter_custom_hashCode_method() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()I", null, null); m.visitInsn(Opcodes.ICONST_0); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_non_hashCode_method() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "hashCode", "()V", null, null); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(); } @Test public void should_filter_generated_equals_method() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "equals", "(Ljava/lang/Object;)Z", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInvokeDynamicInsn("equals", "(LPoint;Ljava/lang/Object;)Z", new Handle(Opcodes.H_INVOKESTATIC, "java/lang/runtime/ObjectMethods", "bootstrap", "(Ljava/lang/invoke/MethodHandles$Lookup;Ljava/lang/String;Ljava/lang/invoke/TypeDescriptor;Ljava/lang/Class;Ljava/lang/String;[Ljava/lang/invoke/MethodHandle;)Ljava/lang/Object;", false)); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_not_filter_custom_equals_method() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "equals", "(Ljava/lang/Object;)Z", null, null); m.visitInsn(Opcodes.ICONST_0); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_non_equals_method() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "equals", "()V", null, null); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_non_records() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "toString", "()Ljava/lang/String;", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitInvokeDynamicInsn("toString", "(LPoint;)Ljava/lang/String;", new Handle(Opcodes.H_INVOKESTATIC, "java/lang/runtime/ObjectMethods", "bootstrap", "(Ljava/lang/invoke/MethodHandles$Lookup;Ljava/lang/String;Ljava/lang/invoke/TypeDescriptor;Ljava/lang/Class;Ljava/lang/String;[Ljava/lang/invoke/MethodHandle;)Ljava/lang/Object;", false)); m.visitInsn(Opcodes.ARETURN); filter.filter(m, context, output); assertIgnored(); } @Test public void should_filter_field_int() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "foo", "()Z", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitFieldInsn(Opcodes.GETFIELD, "Dunno", "foo", "Z"); m.visitInsn(Opcodes.IRETURN); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_filter_field_object() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "foo", "()Ljava/lang/String;", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitFieldInsn(Opcodes.GETFIELD, "Dunno", "foo", "Ljava/lang/String"); m.visitInsn(Opcodes.LRETURN); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_not_filter_redirect_method() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "foo", "()Ljava/lang/String;", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); // The method name is different from the field name m.visitFieldInsn(Opcodes.GETFIELD, "Dunno", "bar", "Ljava/lang/String"); m.visitInsn(Opcodes.LRETURN); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_noreturn_method() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "foo", "()Ljava/lang/String;", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitFieldInsn(Opcodes.GETFIELD, "Dunno", "foo", "Ljava/lang/String"); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_other_method() { context.superClassName = "java/lang/Record"; final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "foo", "()Ljava/lang/String;", null, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitFieldInsn(Opcodes.GETFIELD, "Dunno", "foo", "Ljava/lang/String"); // Not a return statement m.visitFieldInsn(Opcodes.GETFIELD, "Dunno", "foo", "Ljava/lang/String"); filter.filter(m, context, output); assertIgnored(); } } StringSwitchFilterTest.java000066400000000000000000000220631451257705100347140ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import java.util.HashSet; import java.util.Set; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link StringSwitchFilter}. */ public class StringSwitchFilterTest extends FilterTestBase { private final IFilter filter = new StringSwitchFilter(); @Test public void should_filter() { final Set expectedNewTargets = new HashSet(); final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "()V", null, null); final Label case1 = new Label(); final Label case2 = new Label(); final Label case3 = new Label(); final Label caseDefault = new Label(); final Label h1 = new Label(); final Label h2 = new Label(); // filter should not remember this unrelated slot m.visitLdcInsn(""); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitVarInsn(Opcodes.ALOAD, 1); // switch (...) m.visitInsn(Opcodes.DUP); m.visitVarInsn(Opcodes.ASTORE, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "hashCode", "()I", false); m.visitTableSwitchInsn(97, 98, caseDefault, h1, h2); final AbstractInsnNode switchNode = m.instructions.getLast(); m.visitLabel(h1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitLdcInsn("a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); // if equal "a", then goto its case m.visitJumpInsn(Opcodes.IFNE, case1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitLdcInsn("\0a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); // if equal "\0a", then goto its case m.visitJumpInsn(Opcodes.IFNE, case2); // goto default case m.visitJumpInsn(Opcodes.GOTO, caseDefault); m.visitLabel(h2); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitLdcInsn("b"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); // if equal "b", then goto its case m.visitJumpInsn(Opcodes.IFNE, case3); // goto default case m.visitJumpInsn(Opcodes.GOTO, caseDefault); final AbstractInsnNode expectedToInclusive = m.instructions.getLast(); m.visitLabel(case1); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(case2); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(case3); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(caseDefault); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); filter.filter(m, context, output); assertReplacedBranches(switchNode, expectedNewTargets); assertIgnored(new Range(switchNode.getNext(), expectedToInclusive)); } @Test public void should_filter_when_default_is_first() { final Set expectedNewTargets = new HashSet(); final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "()V", null, null); final Label case1 = new Label(); final Label caseDefault = new Label(); final Label h1 = new Label(); // filter should not remember this unrelated slot m.visitLdcInsn(""); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitVarInsn(Opcodes.ALOAD, 1); // switch (...) m.visitInsn(Opcodes.DUP); m.visitVarInsn(Opcodes.ASTORE, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "hashCode", "()I", false); m.visitLookupSwitchInsn(caseDefault, new int[] { 97 }, new Label[] { h1 }); final AbstractInsnNode switchNode = m.instructions.getLast(); m.visitLabel(h1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitLdcInsn("a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); // if equal "a", then goto its case m.visitJumpInsn(Opcodes.IFNE, case1); final AbstractInsnNode expectedToInclusive = m.instructions.getLast(); m.visitLabel(caseDefault); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(case1); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); filter.filter(m, context, output); assertReplacedBranches(switchNode, expectedNewTargets); assertIgnored(new Range(switchNode.getNext(), expectedToInclusive)); } /** *
	 * fun example(p: String) {
	 *   when (p) {
	 *     "a" -> return
	 *     "\u0000a" -> return
	 *     "b" -> return
	 *     "\u0000b" -> return
	 *     "c" -> return
	 *     "\u0000c" -> return
	 *   }
	 * }
	 * 
*/ @Test public void should_filter_Kotlin_1_5() { final Set expectedNewTargets = new HashSet(); final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "example", "()V", null, null); final Label h1 = new Label(); final Label h2 = new Label(); final Label h3 = new Label(); final Label defaultCase = new Label(); final Label case1 = new Label(); final Label case2 = new Label(); final Label case3 = new Label(); final Label case4 = new Label(); final Label case5 = new Label(); final Label case6 = new Label(); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "hashCode", "()I", false); m.visitTableSwitchInsn(97, 99, defaultCase, h1, h2, h3); m.visitLabel(h1); final AbstractInsnNode expectedFromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitLdcInsn("a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); m.visitJumpInsn(Opcodes.IFNE, case1); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitLdcInsn("\u0000a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); m.visitJumpInsn(Opcodes.IFNE, case2); m.visitJumpInsn(Opcodes.GOTO, defaultCase); m.visitLabel(h2); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitLdcInsn("b"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); m.visitJumpInsn(Opcodes.IFNE, case3); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitLdcInsn("\u0000b"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); m.visitJumpInsn(Opcodes.IFNE, case4); m.visitJumpInsn(Opcodes.GOTO, defaultCase); m.visitLabel(h3); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitLdcInsn("c"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); m.visitJumpInsn(Opcodes.IFNE, case5); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitLdcInsn("\u0000c"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); m.visitJumpInsn(Opcodes.IFNE, case6); m.visitJumpInsn(Opcodes.GOTO, defaultCase); final AbstractInsnNode expectedToInclusive = m.instructions.getLast(); m.visitLabel(case1); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(case2); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(case3); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(case4); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(case5); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(case6); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); m.visitLabel(defaultCase); m.visitInsn(Opcodes.RETURN); expectedNewTargets.add(m.instructions.getLast()); filter.filter(m, context, output); assertIgnored(new Range(expectedFromInclusive, expectedToInclusive)); assertReplacedBranches(expectedFromInclusive.getPrevious(), expectedNewTargets); } @Test public void should_not_filter_empty_lookup_switch() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "(Ljava/lang/String;)V", null, null); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ASTORE, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "hashCode", "()I", false); final Label defaultCase = new Label(); m.visitLookupSwitchInsn(defaultCase, null, new Label[] {}); m.visitLabel(defaultCase); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(); } } StringSwitchJavacFilterTest.java000066400000000000000000000142521451257705100356620ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link StringSwitchJavacFilter}. */ public class StringSwitchJavacFilterTest extends FilterTestBase { private final IFilter filter = new StringSwitchJavacFilter(); private final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "()V", null, null); private AbstractInsnNode expectedFromInclusive; private AbstractInsnNode expectedToInclusive; private void createFirstSwitch() { final Label h1 = new Label(); final Label h1_2 = new Label(); final Label h2 = new Label(); final Label secondSwitch = new Label(); m.visitInsn(Opcodes.ICONST_M1); m.visitVarInsn(Opcodes.ISTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "hashCode", "()I", false); m.visitLookupSwitchInsn(secondSwitch, new int[] { 97, 98 }, new Label[] { h1, h2 }); expectedFromInclusive = m.instructions.getLast(); m.visitLabel(h1); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitLdcInsn("a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); // if not equal "a", then goto next comparison m.visitJumpInsn(Opcodes.IFEQ, h1_2); m.visitInsn(Opcodes.ICONST_0); m.visitVarInsn(Opcodes.ISTORE, 2); // goto secondSwitch m.visitJumpInsn(Opcodes.GOTO, secondSwitch); m.visitLabel(h1_2); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitLdcInsn("\0a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); // if not equal "\0a", then goto second switch m.visitJumpInsn(Opcodes.IFEQ, secondSwitch); m.visitInsn(Opcodes.ICONST_1); m.visitVarInsn(Opcodes.ISTORE, 2); // goto secondSwitch m.visitJumpInsn(Opcodes.GOTO, secondSwitch); m.visitLabel(h2); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitLdcInsn("b"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); // if not equal "b", then goto second switch m.visitJumpInsn(Opcodes.IFEQ, secondSwitch); m.visitInsn(Opcodes.ICONST_2); m.visitVarInsn(Opcodes.ISTORE, 2); m.visitLabel(secondSwitch); expectedToInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ILOAD, 2); } @Test public void should_filter_code_generated_by_javac() { createFirstSwitch(); final Label cases = new Label(); m.visitTableSwitchInsn(0, 2, cases); m.visitLabel(cases); filter.filter(m, context, output); assertIgnored(new Range(expectedFromInclusive, expectedToInclusive)); } @Test public void should_filter_when_javac_generates_lookupswitch() { createFirstSwitch(); final Label cases = new Label(); m.visitLookupSwitchInsn(cases, null, new Label[] {}); m.visitLabel(cases); filter.filter(m, context, output); assertIgnored(new Range(expectedFromInclusive, expectedToInclusive)); } /** *
	 * int c = -1;
	 * switch (s.hashCode()) {
	 * case 0:
	 *   if (s.equals(""))
	 *     c = 0;
	 *   return;
	 * default:
	 * }
	 * switch (c)
	 *   // ...
	 * 
*/ @Test public void should_not_filter_when_no_expected_goto() { m.visitInsn(Opcodes.ICONST_M1); m.visitVarInsn(Opcodes.ISTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "hashCode", "()I", false); final Label secondSwitch = new Label(); final Label h1 = new Label(); m.visitTableSwitchInsn(0, 0, secondSwitch, h1); m.visitLabel(h1); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitLdcInsn(""); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); m.visitJumpInsn(Opcodes.IFEQ, secondSwitch); m.visitInsn(Opcodes.ICONST_0); m.visitVarInsn(Opcodes.ISTORE, 2); // Something different from the expected by filter // secondSwitch label or GOTO: m.visitInsn(Opcodes.RETURN); m.visitLabel(secondSwitch); m.visitVarInsn(Opcodes.ILOAD, 2); final Label defaultCase = new Label(); m.visitLookupSwitchInsn(defaultCase, new int[] {}, new Label[] {}); m.visitLabel(defaultCase); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_code_generated_by_ECJ() { final Label h1 = new Label(); final Label h2 = new Label(); final Label cases = new Label(); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "hashCode", "()I", false); m.visitTableSwitchInsn(0, 2, cases, h1, h2); m.visitLabel(h1); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitLdcInsn("a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); // if equal "a", then goto its case m.visitJumpInsn(Opcodes.IFNE, cases); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitLdcInsn("\0a"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); // if equal "\0a", then goto its case m.visitJumpInsn(Opcodes.IFNE, cases); // goto default case m.visitJumpInsn(Opcodes.GOTO, cases); m.visitLabel(h2); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitLdcInsn("b"); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/String", "equals", "(Ljava/lang/Object;)Z", false); // if equal "b", then goto its case m.visitJumpInsn(Opcodes.IFNE, cases); // goto default case m.visitJumpInsn(Opcodes.GOTO, cases); m.visitLabel(cases); filter.filter(m, context, output); assertIgnored(); } } SynchronizedFilterTest.java000066400000000000000000000111021451257705100347330ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.LabelNode; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link SynchronizedFilter}. */ public class SynchronizedFilterTest extends FilterTestBase { private final SynchronizedFilter filter = new SynchronizedFilter(); private final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "()V", null, null); @Test public void javac() { final Label start = new Label(); final Label end = new Label(); final Label handler = new Label(); final Label handlerEnd = new Label(); m.visitTryCatchBlock(start, end, handler, null); m.visitTryCatchBlock(handler, handlerEnd, handler, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitFieldInsn(Opcodes.GETFIELD, "Fun", "lock", "Ljava/lang/Object;"); m.visitInsn(Opcodes.DUP); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitInsn(Opcodes.MONITORENTER); m.visitLabel(start); m.visitInsn(Opcodes.NOP); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.MONITOREXIT); m.visitLabel(end); final Label exit = new Label(); m.visitJumpInsn(Opcodes.GOTO, exit); m.visitLabel(handler); m.visitVarInsn(Opcodes.ASTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.MONITOREXIT); m.visitLabel(handlerEnd); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitInsn(Opcodes.ATHROW); m.visitLabel(exit); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(new Range((LabelNode) handler.info, ((LabelNode) exit.info).getPrevious())); } /** *
	 *     try {
	 *         ...
	 *     } catch (Exception e) {
	 *         ...
	 *     } finally {
	 *         ...
	 *     }
	 * 
*/ @Test public void javacTryCatchFinally() { final Label start = new Label(); final Label end = new Label(); final Label catchHandler = new Label(); final Label finallyHandler = new Label(); final Label catchHandlerEnd = new Label(); m.visitTryCatchBlock(start, end, catchHandler, "java/lang/Exception"); m.visitTryCatchBlock(start, end, finallyHandler, null); m.visitTryCatchBlock(catchHandler, catchHandlerEnd, finallyHandler, null); m.visitLabel(start); // body m.visitInsn(Opcodes.NOP); m.visitLabel(end); // finally m.visitInsn(Opcodes.NOP); final Label exit = new Label(); m.visitJumpInsn(Opcodes.GOTO, exit); m.visitLabel(catchHandler); m.visitVarInsn(Opcodes.ASTORE, 1); // catch m.visitInsn(Opcodes.NOP); m.visitLabel(catchHandlerEnd); // finally m.visitInsn(Opcodes.NOP); m.visitJumpInsn(Opcodes.GOTO, exit); m.visitLabel(finallyHandler); m.visitVarInsn(Opcodes.ASTORE, 2); // finally m.visitInsn(Opcodes.NOP); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitInsn(Opcodes.ATHROW); m.visitLabel(exit); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(); } @Test public void ecj() { final Label start = new Label(); final Label end = new Label(); final Label handler = new Label(); final Label handlerEnd = new Label(); m.visitTryCatchBlock(start, end, handler, null); m.visitTryCatchBlock(handler, handlerEnd, handler, null); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitFieldInsn(Opcodes.GETFIELD, "Target", "lock", "Ljava/lang/Object;"); m.visitInsn(Opcodes.DUP); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitInsn(Opcodes.MONITORENTER); m.visitLabel(start); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitInsn(Opcodes.NOP); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.MONITOREXIT); m.visitLabel(end); final Label exit = new Label(); m.visitJumpInsn(Opcodes.GOTO, exit); m.visitLabel(handler); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.MONITOREXIT); m.visitLabel(handlerEnd); m.visitInsn(Opcodes.ATHROW); m.visitLabel(exit); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertIgnored(new Range((LabelNode) handler.info, ((LabelNode) exit.info).getPrevious())); } } SyntheticFilterTest.java000066400000000000000000000136061451257705100342410ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link SyntheticFilter}. */ public class SyntheticFilterTest extends FilterTestBase { private final SyntheticFilter filter = new SyntheticFilter(); @Test public void testNonSynthetic() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "()V", null, null); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(); } @Test public void testSynthetic() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_SYNTHETIC, "name", "()V", null, null); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void testLambda() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_SYNTHETIC, "lambda$1", "()V", null, null); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(); } @Test public void should_filter_synthetic_method_with_prefix_anonfun_in_non_Scala_classes() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_SYNTHETIC, "$anonfun$main$1", "()V", null, null); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_not_filter_synthetic_method_with_prefix_anonfun_in_Scala_classes() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_SYNTHETIC, "$anonfun$main$1", "()V", null, null); m.visitInsn(Opcodes.RETURN); context.classAttributes.add("ScalaSig"); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_synthetic_method_with_prefix_anonfun_in_Scala_inner_classes() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_SYNTHETIC, "$anonfun$main$1", "()V", null, null); m.visitInsn(Opcodes.RETURN); context.classAttributes.add("Scala"); filter.filter(m, context, output); assertIgnored(); } @Test public void should_not_filter_method_with_suffix_default_in_kotlin_classes() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_SYNTHETIC | Opcodes.ACC_BRIDGE, "example$default", "(LTarget;Ljava/lang/String;Ijava/lang/Object;)V", null, null); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(); } @Test public void should_filter_synthetic_method_with_suffix_default_in_non_kotlin_classes() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_SYNTHETIC | Opcodes.ACC_BRIDGE, "example$default", "(LTarget;Ljava/lang/String;Ijava/lang/Object;)V", null, null); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertMethodIgnored(m); } @Test public void should_not_filter_synthetic_constructor_containing_default_arguments_in_kotlin_classes() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_SYNTHETIC, "", "(IILkotlin/jvm/internal/DefaultConstructorMarker;)V", null, null); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(); } /** * For private suspending function Kotlin compiler versions prior to 1.5 * produce package-local synthetic method that should not be filtered * *
	 * private suspend fun example() {
	 * }
	 * 
* * @see #should_filter_synthetic_methods_whose_name_starts_with_access_dollar_even_if_last_argument_is_kotlin_coroutine_continuation() */ @Test public void should_not_filter_synthetic_methods_whose_last_argument_is_kotlin_coroutine_continuation() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_SYNTHETIC | Opcodes.ACC_STATIC, "example", "(Lkotlin/coroutines/Continuation;)Ljava/lang/Object;", null, null); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(); } /** * For private suspending function Kotlin compiler versions starting from * 1.5 produce additional public synthetic method with name starting with * "access$" that should be filtered * *
	 * private suspend fun example() {
	 * }
	 * 
* * @see #should_not_filter_synthetic_methods_whose_last_argument_is_kotlin_coroutine_continuation() */ @Test public void should_filter_synthetic_methods_whose_name_starts_with_access_dollar_even_if_last_argument_is_kotlin_coroutine_continuation() { final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC | Opcodes.ACC_FINAL | Opcodes.ACC_SYNTHETIC, "access$example", "(Lkotlin/coroutines/Continuation;)Ljava/lang/Object;", null, null); context.classAnnotations .add(KotlinGeneratedFilter.KOTLIN_METADATA_DESC); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitMethodInsn(Opcodes.INVOKESTATIC, "ExampleKt", "example", "(Lkotlin/coroutines/Continuation;)Ljava/lang/Object;", false); m.visitInsn(Opcodes.RETURN); filter.filter(m, context, output); assertMethodIgnored(m); } } TryWithResourcesEcjFilterTest.java000066400000000000000000000405461451257705100362210ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link TryWithResourcesEcjFilter}. */ public class TryWithResourcesEcjFilterTest extends FilterTestBase { private final TryWithResourcesEcjFilter filter = new TryWithResourcesEcjFilter(); private final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "()V", null, null); /** * ECJ for * *
	 *     try (r0 = ...; r1 = ...; r2= ...) {
	 *         ...
	 *     } finally (...) {
	 *         ...
	 *     }
	 *     ...
	 * 
* * generates * *
	 *     ACONST_NULL
	 *     ASTORE primaryExc
	 *     ACONST_NULL
	 *     ASTORE suppressedExc
	 *     ...
	 *     ASTORE r1
	 *     ...
	 *     ASTORE r2
	 *     ...
	 *     ASTORE r3
	 *
	 *     ... // body
	 *
	 *     ALOAD r3
	 *     IFNULL r2_close
	 *     ALOAD r3
	 *     INVOKEVIRTUAL close:()V
	 *     GOTO r2_close
	 *
	 *     ASTORE primaryExc
	 *     ALOAD r3
	 *     IFNULL n
	 *     ALOAD r3
	 *     INVOKEVIRTUAL close:()V
	 *     n:
	 *     ALOAD primaryExc
	 *     ATHROW
	 *
	 *     r2_close:
	 *     ALOAD r2
	 *     IFNULL r1_close
	 *     ALOAD r2
	 *     INVOKEVIRTUAL close:()V
	 *     GOTO r1_close
	 *
	 *     ASTORE suppressedExc
	 *     ALOAD primaryExc
	 *     IFNONNULL s
	 *     ALOAD suppressedExc
	 *     ASTORE primaryExc
	 *     GOTO e
	 *     s:
	 *     ALOAD primaryExc
	 *     ALOAD suppressedExc
	 *     IF_ACMPEQ e
	 *     ALOAD primaryExc
	 *     ALOAD suppressedExc
	 *     INVOKEVIRTUAL java/lang/Throwable.addSuppressed:(Ljava/lang/Throwable;)V
	 *     e:
	 *
	 *     ALOAD r2
	 *     IFNULL n
	 *     ALOAD r2
	 *     INVOKEVIRTUAL close:()V
	 *     n:
	 *     ALOAD primaryExc
	 *     ATHROW
	 *
	 *     r1_close:
	 *     ALOAD r1
	 *     IFNULL after
	 *     ALOAD r1
	 *     INVOKEVIRTUAL close:()V
	 *     GOTO after
	 *
	 *     ASTORE suppressedExc
	 *     ALOAD primaryExc
	 *     IFNONNULL s
	 *     ALOAD suppressedExc
	 *     ASTORE primaryExc
	 *     GOTO e
	 *     s:
	 *     ALOAD primaryExc
	 *     ALOAD suppressedExc
	 *     IF_ACMPEQ e
	 *     ALOAD primaryExc
	 *     ALOAD suppressedExc
	 *     INVOKEVIRTUAL java/lang/Throwable.addSuppressed:(Ljava/lang/Throwable;)V
	 *     e:
	 *
	 *     ALOAD r1
	 *     IFNULL n
	 *     ALOAD r1
	 *     INVOKEVIRTUAL close:()V
	 *     n:
	 *     ALOAD primaryExc
	 *     ATHROW
	 *
	 *     ASTORE suppressedExc
	 *     ALOAD primaryExc
	 *     IFNONNULL s
	 *     ALOAD suppressedExc
	 *     ASTORE primaryExc
	 *     GOTO e
	 *     s:
	 *     ALOAD primaryExc
	 *     ALOAD suppressedExc
	 *     IF_ACMPEQ e
	 *     ALOAD primaryExc
	 *     ALOAD suppressedExc
	 *     INVOKEVIRTUAL java/lang/Throwable.addSuppressed:(Ljava/lang/Throwable;)V
	 *     e:
	 *
	 *     ALOAD primaryExc
	 *     ATHROW
	 *
	 *     ... // additional handlers for catch blocks and finally on exceptional path
	 *
	 *     after:
	 *     ... // finally on normal path
	 *     ...
	 * 
*/ @Test public void ecj() { final Range range0 = new Range(); final Range range1 = new Range(); final Label handler = new Label(); m.visitTryCatchBlock(handler, handler, handler, null); // primaryExc = null m.visitInsn(Opcodes.ACONST_NULL); m.visitVarInsn(Opcodes.ASTORE, 1); // suppressedExc = null m.visitInsn(Opcodes.ACONST_NULL); m.visitVarInsn(Opcodes.ASTORE, 2); // body m.visitInsn(Opcodes.NOP); final Label l4 = new Label(); final Label l7 = new Label(); final Label end = new Label(); { // nextIsEcjClose("r0") m.visitVarInsn(Opcodes.ALOAD, 5); range0.fromInclusive = m.instructions.getLast(); m.visitJumpInsn(Opcodes.IFNULL, l4); m.visitVarInsn(Opcodes.ALOAD, 5); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun2$Resource", "close", "()V", false); } m.visitJumpInsn(Opcodes.GOTO, l4); range0.toInclusive = m.instructions.getLast(); // catch (any primaryExc) m.visitLabel(handler); range1.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 1); { // nextIsEcjCloseAndThrow("r0") m.visitVarInsn(Opcodes.ALOAD, 5); Label l11 = new Label(); m.visitJumpInsn(Opcodes.IFNULL, l11); m.visitVarInsn(Opcodes.ALOAD, 5); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun2$Resource", "close", "()V", false); m.visitLabel(l11); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.ATHROW); } m.visitLabel(l4); { // nextIsEcjClose("r1") m.visitVarInsn(Opcodes.ALOAD, 4); m.visitJumpInsn(Opcodes.IFNULL, l7); m.visitVarInsn(Opcodes.ALOAD, 4); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun2$Resource", "close", "()V", false); } m.visitJumpInsn(Opcodes.GOTO, l7); { // nextIsEcjSuppress m.visitVarInsn(Opcodes.ASTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 1); final Label suppressStart = new Label(); m.visitJumpInsn(Opcodes.IFNONNULL, suppressStart); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ASTORE, 1); final Label suppressEnd = new Label(); m.visitJumpInsn(Opcodes.GOTO, suppressEnd); m.visitLabel(suppressStart); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitJumpInsn(Opcodes.IF_ACMPEQ, suppressEnd); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitLabel(suppressEnd); } { // nextIsEcjCloseAndThrow("r1") m.visitVarInsn(Opcodes.ALOAD, 4); final Label l14 = new Label(); m.visitJumpInsn(Opcodes.IFNULL, l14); m.visitVarInsn(Opcodes.ALOAD, 4); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun2$Resource", "close", "()V", false); m.visitLabel(l14); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.ATHROW); } m.visitLabel(l7); { // nextIsEcjClose("r2") m.visitVarInsn(Opcodes.ALOAD, 3); m.visitJumpInsn(Opcodes.IFNULL, end); m.visitVarInsn(Opcodes.ALOAD, 3); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun2$Resource", "close", "()V", false); m.visitJumpInsn(Opcodes.GOTO, end); } { // nextIsEcjSuppress m.visitVarInsn(Opcodes.ASTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 1); final Label suppressStart = new Label(); m.visitJumpInsn(Opcodes.IFNONNULL, suppressStart); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ASTORE, 1); final Label suppressEnd = new Label(); m.visitJumpInsn(Opcodes.GOTO, suppressEnd); m.visitLabel(suppressStart); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitJumpInsn(Opcodes.IF_ACMPEQ, suppressEnd); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitLabel(suppressEnd); } { // nextIsEcjCloseAndThrow("r2") m.visitVarInsn(Opcodes.ALOAD, 3); final Label l18 = new Label(); m.visitJumpInsn(Opcodes.IFNULL, l18); m.visitVarInsn(Opcodes.ALOAD, 3); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun2$Resource", "close", "()V", false); m.visitLabel(l18); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.ATHROW); } { // nextIsEcjSuppress m.visitVarInsn(Opcodes.ASTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 1); final Label suppressStart = new Label(); m.visitJumpInsn(Opcodes.IFNONNULL, suppressStart); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ASTORE, 1); final Label suppressEnd = new Label(); m.visitJumpInsn(Opcodes.GOTO, suppressEnd); m.visitLabel(suppressStart); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitJumpInsn(Opcodes.IF_ACMPEQ, suppressEnd); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitLabel(suppressEnd); } // throw primaryExc m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.ATHROW); range1.toInclusive = m.instructions.getLast(); // additional handlers m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(range0, range1); } /** * ECJ for * *
	 *     try (r1 = ...; r2 = ...; r3 = ...) {
	 *         return ...
	 *     } finally {
	 *         ...
	 *     }
	 * 
* * generates * *
	 *     ACONST_NULL
	 *     astore primaryExc
	 *     ACONST_NULL
	 *     astore suppressedExc
	 *
	 *     ...
	 *     ASTORE r1
	 *     ...
	 *     ASTORE r2
	 *     ...
	 *     ASTORE r3
	 *
	 *     ... // body
	 *
	 *     ALOAD r3
	 *     IFNULL n
	 *     ALOAD r3
	 *     INVOKEVIRTUAL close:()V
	 *     n:
	 *     ALOAD r2
	 *     IFNULL n
	 *     ALOAD r2
	 *     INVOKEVIRTUAL close:()V
	 *     n:
	 *     ALOAD r1
	 *     IFNULL n
	 *     ALOAD r1
	 *     INVOKEVIRTUAL close:()V
	 *     n:
	 *
	 *     ... // finally on normal path
	 *     ARETURN
	 *
	 *     ASTORE primaryExc
	 *     ALOAD r3
	 *     IFNULL n
	 *     ALOAD r3
	 *     INVOKEVIRTUAL close:()V
	 *     n:
	 *     ALOAD primaryExc
	 *     ATHROW
	 *
	 *     ASTORE suppressedExc
	 *     ALOAD primaryExc
	 *     IFNONNULL s
	 *     ALOAD suppressedExc
	 *     ASTORE primaryExc
	 *     GOTO  e
	 *     s:
	 *     ALOAD primaryExc
	 *     ALOAD suppressedExc
	 *     IF_ACMPEQ  e
	 *     ALOAD primaryExc
	 *     ALOAD suppressedExc
	 *     INVOKEVIRTUAL java/lang/Throwable.addSuppressed:(Ljava/lang/Throwable;)V
	 *     e:
	 *
	 *     ALOAD r2
	 *     IFNULL n
	 *     ALOAD r2
	 *     INVOKEVIRTUAL close:()V
	 *     n:
	 *     ALOAD primaryExc
	 *     ATHROW
	 *
	 *     ASTORE suppressedExc
	 *     ALOAD primaryExc
	 *     IFNONNULL s
	 *     ALOAD suppressedExc
	 *     ASTORE primaryExc
	 *     GOTO e
	 *     s:
	 *     ALOAD primaryExc
	 *     ALOAD suppressedExc
	 *     IF_ACMPEQ e
	 *     ALOAD primaryExc
	 *     ALOAD suppressedExc
	 *     INVOKEVIRTUAL java/lang/Throwable.addSuppressed:(Ljava/lang/Throwable;)V
	 *     e:
	 *
	 *     ALOAD r1
	 *     IFNULL n
	 *     ALOAD r1
	 *     INVOKEVIRTUAL close:()V
	 *     n:
	 *     ALOAD primaryExc
	 *     ATHROW
	 *
	 *     ASTORE suppressedExc
	 *     ALOAD primaryExc
	 *     IFNONNULL s
	 *     ALOAD suppressedExc
	 *     ASTORE primaryExc
	 *     GOTO e
	 *     s:
	 *     ALOAD primaryExc
	 *     ALOAD suppressedExc
	 *     IF_ACMPEQ e
	 *     ALOAD primaryExc
	 *     ALOAD suppressedExc
	 *     INVOKEVIRTUAL java/lang/Throwable.addSuppressed:(Ljava/lang/Throwable;)V
	 *     e:
	 *
	 *     ALOAD primaryExc
	 *     ATHROW
	 *
	 *     ... // additional handlers for catch blocks and finally on exceptional path
	 * 
*/ @Test public void ecj_noFlowOut() { final Range range0 = new Range(); final Range range1 = new Range(); final Label handler = new Label(); m.visitTryCatchBlock(handler, handler, handler, null); // primaryExc = null m.visitInsn(Opcodes.ACONST_NULL); m.visitVarInsn(Opcodes.ASTORE, 1); // suppressedExc = null m.visitInsn(Opcodes.ACONST_NULL); m.visitVarInsn(Opcodes.ASTORE, 2); // body m.visitInsn(Opcodes.NOP); { // nextIsEcjClose("r0") final Label label = new Label(); m.visitVarInsn(Opcodes.ALOAD, 5); range0.fromInclusive = m.instructions.getLast(); m.visitJumpInsn(Opcodes.IFNULL, label); m.visitVarInsn(Opcodes.ALOAD, 5); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun$Resource", "close", "()V", false); m.visitLabel(label); } { // nextIsEcjClose("r1") final Label label = new Label(); m.visitVarInsn(Opcodes.ALOAD, 4); m.visitJumpInsn(Opcodes.IFNULL, label); m.visitVarInsn(Opcodes.ALOAD, 4); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun$Resource", "close", "()V", false); m.visitLabel(label); } { // nextIsEcjClose("r2") final Label label = new Label(); m.visitVarInsn(Opcodes.ALOAD, 3); m.visitJumpInsn(Opcodes.IFNULL, label); m.visitVarInsn(Opcodes.ALOAD, 3); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun$Resource", "close", "()V", false); range0.toInclusive = m.instructions.getLast(); m.visitLabel(label); } // finally m.visitInsn(Opcodes.NOP); m.visitInsn(Opcodes.ARETURN); // catch (any primaryExc) m.visitLabel(handler); range1.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 1); { // nextIsEcjCloseAndThrow("r0") m.visitVarInsn(Opcodes.ALOAD, 5); final Label throwLabel = new Label(); m.visitJumpInsn(Opcodes.IFNULL, throwLabel); m.visitVarInsn(Opcodes.ALOAD, 5); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun$Resource", "close", "()V", false); m.visitLabel(throwLabel); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.ATHROW); } { // nextIsEcjSuppress m.visitVarInsn(Opcodes.ASTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 1); final Label suppressStart = new Label(); m.visitJumpInsn(Opcodes.IFNONNULL, suppressStart); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ASTORE, 1); final Label suppressEnd = new Label(); m.visitJumpInsn(Opcodes.GOTO, suppressEnd); m.visitLabel(suppressStart); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitJumpInsn(Opcodes.IF_ACMPEQ, suppressEnd); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitLabel(suppressEnd); } { // nextIsEcjCloseAndThrow("r1") m.visitVarInsn(Opcodes.ALOAD, 4); final Label throwLabel = new Label(); m.visitJumpInsn(Opcodes.IFNULL, throwLabel); m.visitVarInsn(Opcodes.ALOAD, 4); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun$Resource", "close", "()V", false); m.visitLabel(throwLabel); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.ATHROW); } { // nextIsEcjSuppress m.visitVarInsn(Opcodes.ASTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 1); final Label suppressStart = new Label(); m.visitJumpInsn(Opcodes.IFNONNULL, suppressStart); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ASTORE, 1); final Label suppressEnd = new Label(); m.visitJumpInsn(Opcodes.GOTO, suppressEnd); m.visitLabel(suppressStart); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitJumpInsn(Opcodes.IF_ACMPEQ, suppressEnd); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitLabel(suppressEnd); } { // nextIsEcjCloseAndThrow("r2") m.visitVarInsn(Opcodes.ALOAD, 3); final Label throwLabel = new Label(); m.visitJumpInsn(Opcodes.IFNULL, throwLabel); m.visitVarInsn(Opcodes.ALOAD, 3); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun$Resource", "close", "()V", false); m.visitLabel(throwLabel); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.ATHROW); } { // nextIsEcjSuppress m.visitVarInsn(Opcodes.ASTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 1); final Label suppressStart = new Label(); m.visitJumpInsn(Opcodes.IFNONNULL, suppressStart); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ASTORE, 1); final Label suppressEnd = new Label(); m.visitJumpInsn(Opcodes.GOTO, suppressEnd); m.visitLabel(suppressStart); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitJumpInsn(Opcodes.IF_ACMPEQ, suppressEnd); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitLabel(suppressEnd); } // throw primaryExc m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.ATHROW); range1.toInclusive = m.instructions.getLast(); // additional handlers m.visitInsn(Opcodes.NOP); filter.filter(m, context, output); assertIgnored(range0, range1); } } TryWithResourcesJavac11FilterTest.java000066400000000000000000000077021451257705100367030ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link TryWithResourcesJavac11Filter}. */ public class TryWithResourcesJavac11FilterTest extends FilterTestBase { private final TryWithResourcesJavac11Filter filter = new TryWithResourcesJavac11Filter(); private final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "()V", null, null); /** *
	 *   try (r = new ...) {
	 *     ...
	 *   }
	 * 
*/ @Test public void without_null_check() { final Range range1 = new Range(); final Range range2 = new Range(); final Label e = new Label(); final Label t = new Label(); final Label handler = new Label(); m.visitTryCatchBlock(handler, handler, handler, "java/lang/Throwable"); m.visitInsn(Opcodes.NOP); m.visitVarInsn(Opcodes.ALOAD, 0); range1.fromInclusive = m.instructions.getLast(); m.visitMethodInsn(Opcodes.INVOKEINTERFACE, "Resource", "close", "()V", false); m.visitJumpInsn(Opcodes.GOTO, e); range1.toInclusive = m.instructions.getLast(); m.visitLabel(handler); range2.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitMethodInsn(Opcodes.INVOKEINTERFACE, "Resource", "close", "()V", false); m.visitJumpInsn(Opcodes.GOTO, t); m.visitVarInsn(Opcodes.ASTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitLabel(t); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.ATHROW); range2.toInclusive = m.instructions.getLast(); m.visitLabel(e); filter.filter(m, context, output); assertIgnored(range1, range2); } /** *
	 *   try (r = open()) {
	 *     ...
	 *   }
	 * 
*/ @Test public void with_null_check() { final Range range1 = new Range(); final Range range2 = new Range(); final Label e = new Label(); final Label t = new Label(); final Label handler = new Label(); m.visitTryCatchBlock(handler, handler, handler, "java/lang/Throwable"); m.visitInsn(Opcodes.NOP); m.visitVarInsn(Opcodes.ALOAD, 0); range1.fromInclusive = m.instructions.getLast(); m.visitJumpInsn(Opcodes.IFNULL, e); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitMethodInsn(Opcodes.INVOKEINTERFACE, "Resource", "close", "()V", false); m.visitJumpInsn(Opcodes.GOTO, e); range1.toInclusive = m.instructions.getLast(); m.visitLabel(handler); range2.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 1); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitJumpInsn(Opcodes.IFNULL, t); m.visitVarInsn(Opcodes.ALOAD, 0); m.visitMethodInsn(Opcodes.INVOKEINTERFACE, "Resource", "close", "()V", false); m.visitJumpInsn(Opcodes.GOTO, t); m.visitVarInsn(Opcodes.ASTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitLabel(t); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitInsn(Opcodes.ATHROW); range2.toInclusive = m.instructions.getLast(); m.visitLabel(e); filter.filter(m, context, output); assertIgnored(range1, range2); } } TryWithResourcesJavacFilterTest.java000066400000000000000000000471241451257705100365430ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/analysis/filter/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis.filter; import org.jacoco.core.internal.instr.InstrSupport; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link TryWithResourcesJavacFilter}. */ public class TryWithResourcesJavacFilterTest extends FilterTestBase { private final TryWithResourcesJavacFilter filter = new TryWithResourcesJavacFilter(); private final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0, "name", "()V", null, null); /** * javac 9 for * *
	 *     try (r0 = open(...); r1 = new ...) {
	 *         return ...
	 *     } finally {
	 *         ...
	 *     }
	 * 
* * generates * *
	 *     ...
	 *     ASTORE r0
	 *     ACONST_NULL
	 *     ASTORE primaryExc0
	 *
	 *     ...
	 *     ASTORE r1
	 *     ACONST_NULL
	 *     ASTORE primaryExc1
	 *
	 *     ... // body
	 *
	 *     ALOAD primaryExc1
	 *     ALOAD r1
	 *     INVOKESTATIC $closeResource:(Ljava/lang/Throwable;Ljava/lang/AutoCloseable;)V
	 *
	 *     ALOAD r0
	 *     IFNULL n
	 *     ALOAD primaryExc0
	 *     ALOAD r0
	 *     INVOKESTATIC $closeResource:(Ljava/lang/Throwable;Ljava/lang/AutoCloseable;)V
	 *     n:
	 *
	 *     ... // finally on normal path
	 *     ARETURN
	 *
	 *     ASTORE t
	 *     ALOAD t
	 *     ASTORE primaryExc1
	 *     ALOAD t
	 *     ATHROW
	 *
	 *     ASTORE t
	 *     ALOAD primaryExc1
	 *     ALOAD r1
	 *     INVOKESTATIC  $closeResource:(Ljava/lang/Throwable;Ljava/lang/AutoCloseable;)V
	 *     ALOAD t
	 *     ATHROW
	 *
	 *     ASTORE t
	 *     ALOAD t
	 *     ASTORE primaryExc0
	 *     ALOAD t
	 *     ATHROW
	 *
	 *     ASTORE t
	 *     ALOAD r0
	 *     IFNULL n
	 *     ALOAD primaryExc0
	 *     ALOAD r0
	 *     INVOKESTATIC  $closeResource:(Ljava/lang/Throwable;Ljava/lang/AutoCloseable;)V
	 *     n:
	 *     ALOAD t
	 *     ATHROW
	 *
	 *     ... // additional handlers for catch blocks and finally on exceptional path
	 * 
*/ @Test public void javac9() { final Range range0 = new Range(); final Range range1 = new Range(); final Range range2 = new Range(); final Range range3 = new Range(); final Label handler1 = new Label(); m.visitTryCatchBlock(handler1, handler1, handler1, "java/lang/Throwable"); final Label handler2 = new Label(); m.visitTryCatchBlock(handler2, handler2, handler2, "java/lang/Throwable"); // r0 = open(...) m.visitVarInsn(Opcodes.ASTORE, 1); // primaryExc0 = null m.visitInsn(Opcodes.ACONST_NULL); m.visitVarInsn(Opcodes.ASTORE, 2); // r1 = new .. m.visitVarInsn(Opcodes.ASTORE, 3); // primaryExc1 = null m.visitInsn(Opcodes.ACONST_NULL); m.visitVarInsn(Opcodes.ASTORE, 4); // body m.visitInsn(Opcodes.NOP); m.visitInsn(Opcodes.ACONST_NULL); m.visitVarInsn(Opcodes.ASTORE, 5); // $closeResource(primaryExc1, r1) m.visitVarInsn(Opcodes.ALOAD, 4); range0.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ALOAD, 3); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Fun", "$closeResource", "(Ljava/lang/Throwable;Ljava/lang/AutoCloseable;)V", false); range0.toInclusive = m.instructions.getLast(); // if (r0 != null) m.visitVarInsn(Opcodes.ALOAD, 1); range2.fromInclusive = m.instructions.getLast(); final Label l11 = new Label(); m.visitJumpInsn(Opcodes.IFNULL, l11); // $closeResource(primaryExc0, r0) m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Fun", "$closeResource", "(Ljava/lang/Throwable;Ljava/lang/AutoCloseable;)V", false); range2.toInclusive = m.instructions.getLast(); m.visitLabel(l11); // finally m.visitInsn(Opcodes.NOP); m.visitVarInsn(Opcodes.ALOAD, 5); m.visitInsn(Opcodes.ARETURN); // catch (Throwable t) m.visitLabel(handler1); range1.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 5); // primaryExc1 = t m.visitVarInsn(Opcodes.ALOAD, 5); m.visitVarInsn(Opcodes.ASTORE, 4); // throw t m.visitVarInsn(Opcodes.ALOAD, 5); m.visitInsn(Opcodes.ATHROW); // catch (any t) m.visitVarInsn(Opcodes.ASTORE, 6); // $closeResource(primaryExc1, r1) m.visitVarInsn(Opcodes.ALOAD, 4); m.visitVarInsn(Opcodes.ALOAD, 3); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Fun", "$closeResource", "(Ljava/lang/Throwable;Ljava/lang/AutoCloseable;)V", false); m.visitVarInsn(Opcodes.ALOAD, 6); m.visitInsn(Opcodes.ATHROW); range1.toInclusive = m.instructions.getLast(); // catch (Throwable t) m.visitLabel(handler2); range3.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 3); // primaryExc0 = t m.visitVarInsn(Opcodes.ALOAD, 3); m.visitVarInsn(Opcodes.ASTORE, 2); // throw t m.visitVarInsn(Opcodes.ALOAD, 3); m.visitInsn(Opcodes.ATHROW); // catch (any t) m.visitVarInsn(Opcodes.ASTORE, 7); // if (r0 != null) m.visitVarInsn(Opcodes.ALOAD, 1); final Label l14 = new Label(); m.visitJumpInsn(Opcodes.IFNULL, l14); // $closeResource(primaryExc0, r0) m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Fun", "$closeResource", "(Ljava/lang/Throwable;Ljava/lang/AutoCloseable;)V", false); m.visitLabel(l14); // throw t m.visitVarInsn(Opcodes.ALOAD, 7); m.visitInsn(Opcodes.ATHROW); range3.toInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 8); // finally m.visitInsn(Opcodes.NOP); m.visitVarInsn(Opcodes.ALOAD, 8); m.visitInsn(Opcodes.ATHROW); filter.filter(m, context, output); assertIgnored(range0, range1, range2, range3); } /** * javac 7 and 8 for * *
	 *     try (r0 = ...; r1 = ...) {
	 *         return ...
	 *     } finally {
	 *         ...
	 *     }
	 * 
* * generate * *
	 *     ...
	 *     ASTORE r0
	 *     ACONST_NULL
	 *     ASTORE primaryExc0
	 *
	 *     ...
	 *     ASTORE r1
	 *     ACONST_NULL
	 *     ASTORE primaryExc1
	 *
	 *     ... // body
	 *
	 *     ALOAD r1
	 *     IFNULL n
	 *     ALOAD primaryExc1
	 *     IFNULL c
	 *     ALOAD r1
	 *     INVOKEINTERFACE close:()V
	 *     GOTO n
	 *     ASTORE t
	 *     ALOAD primaryExc1
	 *     ALOAD t
	 *     INVOKEVIRTUAL java/lang/Throwable.addSuppressed:(Ljava/lang/Throwable;)V
	 *     GOTO n
	 *     c:
	 *     ALOAD r1
	 *     INVOKEINTERFACE close:()V
	 *     n:
	 *
	 *     ALOAD r0
	 *     IFNULL n
	 *     ALOAD primaryExc0
	 *     IFNULL c
	 *     ALOAD r0
	 *     INVOKEVIRTUAL close:()V
	 *     GOTO n
	 *     ASTORE t
	 *     ALOAD primaryExc0
	 *     ALOAD t
	 *     INVOKEVIRTUAL java/lang/Throwable.addSuppressed:(Ljava/lang/Throwable;)V
	 *     GOTO n
	 *     c:
	 *     ALOAD r0
	 *     INVOKEVIRTUAL close:()V
	 *     n:
	 *
	 *     ... // finally on normal path
	 *     ARETURN
	 *
	 *     ASTORE t
	 *     ALOAD t
	 *     ASTORE primaryExc1
	 *     ALOAD t
	 *     ATHROW
	 *
	 *     ASTORE t1
	 *     ALOAD r1
	 *     IFNULL e
	 *     ALOAD primaryExc1
	 *     IFNULL c
	 *     ALOAD r1
	 *     INVOKEINTERFACE close:()V
	 *     GOTO e
	 *     ASTORE t2
	 *     ALOAD primaryExc1
	 *     ALOAD t2
	 *     INVOKEVIRTUAL java/lang/Throwable.addSuppressed:(Ljava/lang/Throwable;)V
	 *     GOTO e
	 *     c:
	 *     ALOAD r1
	 *     INVOKEINTERFACE close:()V
	 *     e:
	 *     ALOAD t1
	 *     ATHROW
	 *
	 *     ASTORE t
	 *     ALOAD t
	 *     ASTORE primaryExc0
	 *     ALOAD t
	 *     ATHROW
	 *
	 *     ASTORE t1
	 *     ALOAD r0
	 *     IFNULL e
	 *     ALOAD primaryExc0
	 *     IFNULL c
	 *     ALOAD r0
	 *     INVOKEVIRTUAL close:()V
	 *     GOTO e
	 *     ASTORE t2
	 *     ALOAD primaryExc0
	 *     ALOAD t2
	 *     INVOKEVIRTUAL java/lang/Throwable.addSuppressed:(Ljava/lang/Throwable;)V
	 *     GOTO e
	 *     c:
	 *     ALOAD r0
	 *     INVOKEVIRTUAL close:()V
	 *     e:
	 *     ALOAD t1
	 *     ATHROW
	 *
	 *     ... // additional handlers for catch blocks and finally on exceptional path
	 * 
*/ @Test public void javac_7_8() { final Range range0 = new Range(); final Range range1 = new Range(); final Range range2 = new Range(); final Range range3 = new Range(); final Label handler1 = new Label(); m.visitTryCatchBlock(handler1, handler1, handler1, "java/lang/Throwable"); final Label handler2 = new Label(); m.visitTryCatchBlock(handler2, handler2, handler2, "java/lang/Throwable"); // r1 = ... m.visitVarInsn(Opcodes.ASTORE, 1); // primaryExc1 = null m.visitInsn(Opcodes.ACONST_NULL); m.visitVarInsn(Opcodes.ASTORE, 2); // r2 = ... m.visitVarInsn(Opcodes.ASTORE, 3); // primaryExc2 = null m.visitInsn(Opcodes.ACONST_NULL); m.visitVarInsn(Opcodes.ASTORE, 4); // body m.visitInsn(Opcodes.NOP); m.visitInsn(Opcodes.ACONST_NULL); m.visitVarInsn(Opcodes.ASTORE, 5); final Label l15 = new Label(); // if (r2 != null) m.visitVarInsn(Opcodes.ALOAD, 3); range0.fromInclusive = m.instructions.getLast(); m.visitJumpInsn(Opcodes.IFNULL, l15); // if (primaryExc2 != null) m.visitVarInsn(Opcodes.ALOAD, 4); final Label l26 = new Label(); m.visitJumpInsn(Opcodes.IFNULL, l26); // r2.close m.visitVarInsn(Opcodes.ALOAD, 3); m.visitMethodInsn(Opcodes.INVOKEINTERFACE, "Fun$Resource2", "close", "()V", false); m.visitJumpInsn(Opcodes.GOTO, l15); m.visitVarInsn(Opcodes.ASTORE, 6); m.visitVarInsn(Opcodes.ALOAD, 4); m.visitVarInsn(Opcodes.ALOAD, 6); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitJumpInsn(Opcodes.GOTO, l15); m.visitLabel(l26); // r2.close m.visitVarInsn(Opcodes.ALOAD, 3); m.visitMethodInsn(Opcodes.INVOKEINTERFACE, "Fun$Resource2", "close", "()V", false); range0.toInclusive = m.instructions.getLast(); m.visitLabel(l15); // if (r1 != null) m.visitVarInsn(Opcodes.ALOAD, 1); range2.fromInclusive = m.instructions.getLast(); final Label l23 = new Label(); m.visitJumpInsn(Opcodes.IFNULL, l23); // if (primaryExc1 != null) m.visitVarInsn(Opcodes.ALOAD, 2); final Label l27 = new Label(); m.visitJumpInsn(Opcodes.IFNULL, l27); // r1.close m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun$Resource1", "close", "()V", false); m.visitJumpInsn(Opcodes.GOTO, l23); m.visitVarInsn(Opcodes.ASTORE, 6); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ALOAD, 6); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitJumpInsn(Opcodes.GOTO, l23); m.visitLabel(l27); // r1.close m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun$Resource1", "close", "()V", false); range2.toInclusive = m.instructions.getLast(); m.visitLabel(l23); // finally m.visitInsn(Opcodes.NOP); m.visitInsn(Opcodes.ARETURN); // catch (Throwable t) m.visitLabel(handler1); range1.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 5); // primaryExc2 = t m.visitVarInsn(Opcodes.ALOAD, 5); m.visitVarInsn(Opcodes.ASTORE, 4); // throw t m.visitVarInsn(Opcodes.ALOAD, 5); m.visitInsn(Opcodes.ATHROW); // catch (any t) m.visitVarInsn(Opcodes.ASTORE, 7); // if (r2 != null) m.visitVarInsn(Opcodes.ALOAD, 3); final Label l28 = new Label(); m.visitJumpInsn(Opcodes.IFNULL, l28); // if (primaryExc2 != null) m.visitVarInsn(Opcodes.ALOAD, 4); final Label l29 = new Label(); m.visitJumpInsn(Opcodes.IFNULL, l29); // r2.close m.visitVarInsn(Opcodes.ALOAD, 3); m.visitMethodInsn(Opcodes.INVOKEINTERFACE, "Fun$Resource2", "close", "()V", false); m.visitJumpInsn(Opcodes.GOTO, l28); m.visitVarInsn(Opcodes.ASTORE, 8); m.visitVarInsn(Opcodes.ALOAD, 4); m.visitVarInsn(Opcodes.ALOAD, 8); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitJumpInsn(Opcodes.GOTO, l28); m.visitLabel(l29); // r2.close m.visitVarInsn(Opcodes.ALOAD, 3); m.visitMethodInsn(Opcodes.INVOKEINTERFACE, "Fun$Resource2", "close", "()V", false); m.visitLabel(l28); // throw t m.visitVarInsn(Opcodes.ALOAD, 7); m.visitInsn(Opcodes.ATHROW); range1.toInclusive = m.instructions.getLast(); // catch (Throwable t) m.visitLabel(handler2); range3.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 3); // primaryExc2 = t m.visitVarInsn(Opcodes.ALOAD, 3); m.visitVarInsn(Opcodes.ASTORE, 2); // throw t m.visitVarInsn(Opcodes.ALOAD, 3); m.visitInsn(Opcodes.ATHROW); // catch (any t) m.visitVarInsn(Opcodes.ASTORE, 9); // if (r1 != null) m.visitVarInsn(Opcodes.ALOAD, 1); final Label l30 = new Label(); m.visitJumpInsn(Opcodes.IFNULL, l30); // if (primaryExc1 != null) m.visitVarInsn(Opcodes.ALOAD, 2); final Label l31 = new Label(); m.visitJumpInsn(Opcodes.IFNULL, l31); // r1.close m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun$Resource1", "close", "()V", false); m.visitJumpInsn(Opcodes.GOTO, l30); m.visitVarInsn(Opcodes.ASTORE, 10); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ALOAD, 10); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitJumpInsn(Opcodes.GOTO, l30); m.visitLabel(l31); // r1.close m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Fun$Resource1", "close", "()V", false); m.visitLabel(l30); // throw t m.visitVarInsn(Opcodes.ALOAD, 9); m.visitInsn(Opcodes.ATHROW); range3.toInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 11); // finally m.visitInsn(Opcodes.NOP); m.visitVarInsn(Opcodes.ALOAD, 11); m.visitInsn(Opcodes.ATHROW); filter.filter(m, context, output); assertIgnored(range0, range1, range2, range3); } /** * javac 9 for * *
	 *     try (r = new ...) {
	 *         ...
	 *     } finally {
	 *         ...
	 *     }
	 * 
* * generates * *
	 *     ...
	 *     ASTORE r
	 *     ACONST_NULL
	 *     ASTORE primaryExc
	 *
	 *     ... // body
	 *
	 *     ALOAD primaryExc
	 *     IFNULL c
	 *     ALOAD r
	 *     INVOKEVIRTUAL close:()V
	 *     GOTO f
	 *     ASTORE t
	 *     ALOAD primaryExc
	 *     ALOAD t
	 *     NVOKEVIRTUAL java/lang/Throwable.addSuppressed:(Ljava/lang/Throwable;)V
	 *     GOTO f
	 *     c:
	 *     ALOAD r
	 *     INVOKEVIRTUAL close:()V
	 *     GOTO f
	 *
	 *     ASTORE t
	 *     ALOAD t
	 *     ASTORE primaryExc
	 *     ALOAD t
	 *     ATHROW
	 *
	 *     ASTORE t
	 *     ALOAD primaryExc
	 *     IFNULL c
	 *     ALOAD r
	 *     INVOKEVIRTUAL close:()V
	 *     GOTO L78
	 *     ASTORE t2
	 *     ALOAD primaryExc
	 *     ALOAD t2
	 *     INVOKEVIRTUAL java/lang/Throwable.addSuppressed:(Ljava/lang/Throwable;)V
	 *     goto e
	 *     c:
	 *     ALOAD r
	 *     INVOKEVIRTUAL close:()V
	 *     e:
	 *     ALOAD t
	 *     ATHROW
	 *
	 *     f:
	 *     ... // finally on normal path
	 *     ... // additional handlers for catch blocks and finally on exceptional path
	 *     ...
	 * 
*/ @Test public void javac9_omitted_null_check() { final Range range0 = new Range(); final Range range1 = new Range(); final Label handler = new Label(); m.visitTryCatchBlock(handler, handler, handler, "java/lang/Throwable"); // primaryExc = null m.visitInsn(Opcodes.ACONST_NULL); m.visitVarInsn(Opcodes.ASTORE, 1); // r = new ... m.visitInsn(Opcodes.NOP); final Label end = new Label(); // "finally" on a normal path { // if (primaryExc != null) m.visitVarInsn(Opcodes.ALOAD, 2); range0.fromInclusive = m.instructions.getLast(); final Label closeLabel = new Label(); m.visitJumpInsn(Opcodes.IFNULL, closeLabel); // r.close m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Resource", "close", "()V", false); m.visitJumpInsn(Opcodes.GOTO, end); // catch (Throwable t) m.visitVarInsn(Opcodes.ASTORE, 3); // primaryExc.addSuppressed(t) m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ALOAD, 3); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitJumpInsn(Opcodes.GOTO, end); m.visitLabel(closeLabel); // r.close() m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Resource", "close", "()V", false); } m.visitJumpInsn(Opcodes.GOTO, end); range0.toInclusive = m.instructions.getLast(); // catch (Throwable t) m.visitLabel(handler); { range1.fromInclusive = m.instructions.getLast(); m.visitVarInsn(Opcodes.ASTORE, 3); // primaryExc = t m.visitVarInsn(Opcodes.ALOAD, 3); m.visitVarInsn(Opcodes.ASTORE, 2); // throw t m.visitVarInsn(Opcodes.ALOAD, 3); m.visitInsn(Opcodes.ATHROW); } // catch (any t) m.visitVarInsn(Opcodes.ASTORE, 4); // "finally" on exceptional path { // if (primaryExc != null) m.visitVarInsn(Opcodes.ALOAD, 2); final Label closeLabel = new Label(); m.visitJumpInsn(Opcodes.IFNULL, closeLabel); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Resource", "close", "()V", false); final Label finallyEndLabel = new Label(); m.visitJumpInsn(Opcodes.GOTO, finallyEndLabel); // catch (Throwable t) m.visitVarInsn(Opcodes.ASTORE, 5); // primaryExc.addSuppressed(t) m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ALOAD, 5); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/lang/Throwable", "addSuppressed", "(Ljava/lang/Throwable;)V", false); m.visitJumpInsn(Opcodes.GOTO, finallyEndLabel); m.visitLabel(closeLabel); // r.close() m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "Resource", "close", "()V", false); m.visitLabel(finallyEndLabel); } // throw t m.visitVarInsn(Opcodes.ALOAD, 4); m.visitInsn(Opcodes.ATHROW); range1.toInclusive = m.instructions.getLast(); m.visitLabel(end); filter.filter(m, context, output); assertIgnored(range0, range1); } /** * javac 9 for * *
	 *     try (r = new ...) {
	 *       throw ...
	 *     }
	 * 
* * generates * *
	 *     ...
	 *     ASTORE r
	 *     ACONST_NULL
	 *     ASTORE primaryExc
	 *
	 *     ...
	 *     ATHROW
	 *
	 *     ASTORE t
	 *     ALOAD t
	 *     ASTORE primaryExc
	 *     ALOAD t
	 *     ATHROW
	 *
	 *     ASTORE t
	 *     ALOAD primaryExc
	 *     ALOAD r
	 *     INVOKESTATIC  $closeResource:(Ljava/lang/Throwable;Ljava/lang/AutoCloseable;)V
	 *     ALOAD t
	 *     ATHROW
	 * 
*/ @Test public void only_exceptional_path() { final Label start = new Label(); final Label handler = new Label(); m.visitTryCatchBlock(start, handler, handler, "java/lang/Throwable"); m.visitLabel(start); m.visitInsn(Opcodes.ATHROW); m.visitLabel(handler); m.visitVarInsn(Opcodes.ASTORE, 3); m.visitVarInsn(Opcodes.ALOAD, 3); m.visitVarInsn(Opcodes.ASTORE, 2); m.visitVarInsn(Opcodes.ALOAD, 3); m.visitInsn(Opcodes.ATHROW); m.visitVarInsn(Opcodes.ASTORE, 4); m.visitVarInsn(Opcodes.ALOAD, 2); m.visitVarInsn(Opcodes.ALOAD, 1); m.visitMethodInsn(Opcodes.INVOKESTATIC, "Fun", "$closeResource", "(Ljava/lang/Throwable;Ljava/lang/AutoCloseable;)V", false); m.visitVarInsn(Opcodes.ALOAD, 4); m.visitInsn(Opcodes.ATHROW); filter.filter(m, context, output); assertIgnored(); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/data/000077500000000000000000000000001451257705100252705ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/data/CRC64Test.java000066400000000000000000000053201451257705100275540ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.data; import static org.junit.Assert.assertEquals; import java.io.UnsupportedEncodingException; import org.jacoco.core.data.ExecutionDataWriter; import org.junit.Test; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.Opcodes; /** * Unit tests for {@link CRC64}. */ public class CRC64Test { @Test public void except_java_9_checksums_should_be_different_for_different_bytecode_versions() { assertEquals(0x589E9080A572741EL, CRC64.classId(createClass(Opcodes.V10))); // should remove workaround for Java 9 // during change of exec file version assertEquals(0x1007, ExecutionDataWriter.FORMAT_VERSION); assertEquals(0xB5284860A572741CL, CRC64.classId(createClass(Opcodes.V9))); assertEquals(0xB5284860A572741CL, CRC64.classId(createClass(Opcodes.V1_8))); assertEquals(0x45284D30A572741AL, CRC64.classId(createClass(Opcodes.V1_7))); } private static byte[] createClass(final int version) { final ClassWriter cw = new ClassWriter(0); cw.visit(version, 0, "Foo", null, "java/lang/Object", null); cw.visitEnd(); cw.toByteArray(); return cw.toByteArray(); } @Test public void test0() { final long sum = CRC64.classId(new byte[0]); assertEquals(0L, sum); } /** * Example taken from http://swissknife.sourceforge.net/docs/CRC64.html * * @throws UnsupportedEncodingException */ @Test public void test1() throws UnsupportedEncodingException { final long sum = CRC64.classId("IHATEMATH".getBytes("ASCII")); assertEquals(0xE3DCADD69B01ADD1L, sum); } /** * Example generated with http://fsumfe.sourceforge.net/ * * @throws UnsupportedEncodingException */ @Test public void test2() { final long sum = CRC64.classId( new byte[] { (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff }); assertEquals(0x5300000000000000L, sum); } /** * Example generated with http://fsumfe.sourceforge.net/ * * @throws UnsupportedEncodingException */ @Test public void test3() throws UnsupportedEncodingException { final long sum = CRC64 .classId("JACOCO_JACOCO_JACOCO_JACOCO".getBytes("ASCII")); assertEquals(0xD8016B38AAD48308L, sum); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/data/CompactDataInputOutputTest.java000066400000000000000000000057251451257705100334250ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.data; import static org.junit.Assert.assertEquals; import java.io.IOException; import java.io.PipedInputStream; import java.io.PipedOutputStream; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link CompactDataInput} and {@link CompactDataOutput}. The * tests don't care about the written binary format, they just verify symmetry. */ public class CompactDataInputOutputTest { private CompactDataOutput out; private CompactDataInput in; @Before public void setup() throws IOException { PipedOutputStream pipe = new PipedOutputStream(); out = new CompactDataOutput(pipe); in = new CompactDataInput(new PipedInputStream(pipe)); } @Test public void testVarInt0x00000000() throws IOException { testVarInt(0x00000000); } @Test public void testVarInt0x0000007F() throws IOException { testVarInt(0x0000007F); } @Test public void testVarInt0x00000080() throws IOException { testVarInt(0x00000080); } @Test public void testVarInt0x00000100() throws IOException { testVarInt(0x00000100); } @Test public void testVarInt0x12345678() throws IOException { testVarInt(0x12345678); } @Test public void testVarIntMinus1() throws IOException { testVarInt(-1); } @Test public void testVarIntMinValue() throws IOException { testVarInt(Integer.MIN_VALUE); } @Test public void testVarIntMaxValue() throws IOException { testVarInt(Integer.MAX_VALUE); } private void testVarInt(int value) throws IOException { out.writeVarInt(value); out.close(); assertEquals(Long.valueOf(value), Long.valueOf(in.readVarInt())); assertEquals(Integer.valueOf(-1), Integer.valueOf(in.read())); } @Test public void testPackedBooleanEmpty() throws IOException { testPackedBoolean(); } @Test public void testPackedBoolean3() throws IOException { testPackedBoolean(false, false, true); } @Test public void testPackedBoolean8() throws IOException { testPackedBoolean(true, false, true, false, false, true, false, true); } @Test public void testPackedBoolean9() throws IOException { testPackedBoolean(true, true, false, true, false, false, true, false, true); } private void testPackedBoolean(boolean... values) throws IOException { out.writeBooleanArray(values); out.close(); final boolean[] actual = in.readBooleanArray(); for (int i = 0; i < values.length; i++) { assertEquals("Index " + i, Boolean.valueOf(values[i]), Boolean.valueOf(actual[i])); } } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/flow/000077500000000000000000000000001451257705100253265ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/flow/ClassProbesAdapterTest.java000066400000000000000000000131411451257705100325520ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.flow; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import org.junit.Test; import org.objectweb.asm.ClassVisitor; import org.objectweb.asm.Label; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; /** * Unit tests for {@link ClassProbesAdapter}. */ public class ClassProbesAdapterTest { private static class MockMethodVisitor extends MethodProbesVisitor { boolean frame = false; @Override public void visitJumpInsnWithProbe(int opcode, Label label, int probeId, IFrame frame) { frame.accept(this); } @Override public void visitTableSwitchInsnWithProbes(int min, int max, Label dflt, Label[] labels, IFrame frame) { frame.accept(this); } @Override public void visitLookupSwitchInsnWithProbes(Label dflt, int[] keys, Label[] labels, IFrame frame) { frame.accept(this); } @Override public void visitFrame(int type, int nLocal, Object[] local, int nStack, Object[] stack) { frame = true; } } private static class MockClassVisitor extends ClassProbesVisitor { int count; @Override public MethodProbesVisitor visitMethod(int access, String name, String desc, String signature, String[] exceptions) { return null; } @Override public void visitTotalProbeCount(int count) { this.count = count; } } @Test public void testProbeCounter() { final MockClassVisitor cv = new MockClassVisitor(); final ClassProbesAdapter adapter = new ClassProbesAdapter(cv, false); assertEquals(0, adapter.nextId()); assertEquals(1, adapter.nextId()); assertEquals(2, adapter.nextId()); adapter.visitEnd(); assertEquals(3, cv.count); } @Test public void testVisitClassMethods() { final MockClassVisitor cv = new MockClassVisitor() { @Override public MethodProbesVisitor visitMethod(int access, String name, String desc, String signature, String[] exceptions) { return new MockMethodVisitor(); } }; final ClassProbesAdapter adapter = new ClassProbesAdapter(cv, false); adapter.visit(Opcodes.V1_5, 0, "Foo", null, "java/lang/Object", null); writeMethod(adapter); writeMethod(adapter); writeMethod(adapter); assertEquals(0, cv.count); adapter.visitEnd(); assertEquals(3, cv.count); } @Test public void testVisitMethodNullMethodVisitor() { final MockClassVisitor cv = new MockClassVisitor(); final ClassProbesAdapter adapter = new ClassProbesAdapter(cv, false); writeMethod(adapter); // 1 probe writeMethodWithBranch(adapter); // 3 probes writeMethodWithTableSwitch(adapter); // 3 probes writeMethodWithLookupSwitch(adapter); // 3 probes adapter.visitEnd(); assertEquals(10, cv.count); } @Test public void testVisitWithFrames() { final MockMethodVisitor mv = new MockMethodVisitor(); final MockClassVisitor cv = new MockClassVisitor() { @Override public MethodProbesVisitor visitMethod(int access, String name, String desc, String signature, String[] exceptions) { return mv; } }; final ClassProbesAdapter adapter = new ClassProbesAdapter(cv, true); writeMethodWithBranch(adapter); adapter.visitEnd(); assertTrue(mv.frame); } @Test public void testVisitWithoutFrames() { final MockMethodVisitor mv = new MockMethodVisitor(); final MockClassVisitor cv = new MockClassVisitor() { @Override public MethodProbesVisitor visitMethod(int access, String name, String desc, String signature, String[] exceptions) { return mv; } }; final ClassProbesAdapter adapter = new ClassProbesAdapter(cv, false); writeMethodWithBranch(adapter); adapter.visitEnd(); assertFalse(mv.frame); } private void writeMethod(final ClassVisitor cv) { MethodVisitor mv = cv.visitMethod(0, "foo", "()V", null, null); mv.visitCode(); mv.visitInsn(Opcodes.RETURN); mv.visitMaxs(0, 1); mv.visitEnd(); } private void writeMethodWithBranch(final ClassVisitor cv) { MethodVisitor mv = cv.visitMethod(0, "foo", "()V", null, null); mv.visitCode(); mv.visitInsn(Opcodes.ICONST_0); Label l = new Label(); mv.visitJumpInsn(Opcodes.IFEQ, l); mv.visitInsn(Opcodes.NOP); mv.visitLabel(l); mv.visitInsn(Opcodes.RETURN); mv.visitMaxs(1, 1); mv.visitEnd(); } private void writeMethodWithTableSwitch(final ClassVisitor cv) { MethodVisitor mv = cv.visitMethod(0, "foo", "()V", null, null); mv.visitCode(); mv.visitInsn(Opcodes.ICONST_0); Label l1 = new Label(); Label l2 = new Label(); mv.visitTableSwitchInsn(0, 0, l1, new Label[] { l2 }); mv.visitLabel(l1); mv.visitInsn(Opcodes.NOP); mv.visitLabel(l2); mv.visitInsn(Opcodes.RETURN); mv.visitMaxs(1, 1); mv.visitEnd(); } private void writeMethodWithLookupSwitch(final ClassVisitor cv) { MethodVisitor mv = cv.visitMethod(0, "foo", "()V", null, null); mv.visitCode(); mv.visitInsn(Opcodes.ICONST_0); Label l1 = new Label(); Label l2 = new Label(); mv.visitLookupSwitchInsn(l1, new int[] { 0 }, new Label[] { l2 }); mv.visitLabel(l1); mv.visitInsn(Opcodes.NOP); mv.visitLabel(l2); mv.visitInsn(Opcodes.RETURN); mv.visitMaxs(1, 1); mv.visitEnd(); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/flow/FrameSnapshotTest.java000066400000000000000000000076151451257705100316140ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.flow; import static org.junit.Assert.assertEquals; import org.jacoco.core.instr.MethodRecorder; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; import org.objectweb.asm.commons.AnalyzerAdapter; /** * Unit tests for {@link FrameSnapshot}. */ public class FrameSnapshotTest { private AnalyzerAdapter analyzer; private IFrame frame; private MethodRecorder expected; private MethodVisitor expectedVisitor; @Before public void setup() { analyzer = new AnalyzerAdapter("Foo", 0, "doit", "()V", null); expected = new MethodRecorder(); expectedVisitor = expected.getVisitor(); } @After public void teardown() { MethodRecorder actual = new MethodRecorder(); frame.accept(actual.getVisitor()); assertEquals(expected, actual); } @Test public void should_not_capture_frame_when_no_analyzer_is_given() { frame = FrameSnapshot.create(null, 0); } @Test public void should_not_capture_frame_when_no_frame_is_defined() { analyzer.visitJumpInsn(Opcodes.GOTO, new Label()); frame = FrameSnapshot.create(analyzer, 0); } @Test public void should_capture_frame_when_frame_is_defined() { analyzer.visitInsn(Opcodes.FCONST_0); analyzer.visitVarInsn(Opcodes.FSTORE, 1); analyzer.visitInsn(Opcodes.ICONST_0); frame = FrameSnapshot.create(analyzer, 0); expectedVisitor.visitFrame(Opcodes.F_FULL, 2, arr("Foo", Opcodes.FLOAT), 1, arr(Opcodes.INTEGER)); } @Test public void should_combine_slots_when_doube_or_long_types_are_given() { analyzer.visitInsn(Opcodes.DCONST_0); analyzer.visitVarInsn(Opcodes.DSTORE, 1); analyzer.visitInsn(Opcodes.FCONST_0); analyzer.visitVarInsn(Opcodes.FSTORE, 3); analyzer.visitInsn(Opcodes.ICONST_0); analyzer.visitInsn(Opcodes.LCONST_0); analyzer.visitInsn(Opcodes.ICONST_0); analyzer.visitInsn(Opcodes.DCONST_0); frame = FrameSnapshot.create(analyzer, 0); final Object[] vars = arr("Foo", Opcodes.DOUBLE, Opcodes.FLOAT); final Object[] stack = arr(Opcodes.INTEGER, Opcodes.LONG, Opcodes.INTEGER, Opcodes.DOUBLE); expectedVisitor.visitFrame(Opcodes.F_FULL, 3, vars, 4, stack); } @Test public void should_decrease_stack_when_popCount_is_given() { analyzer.visitInsn(Opcodes.ICONST_0); analyzer.visitInsn(Opcodes.LCONST_0); analyzer.visitInsn(Opcodes.ICONST_0); analyzer.visitInsn(Opcodes.ICONST_0); frame = FrameSnapshot.create(analyzer, 2); final Object[] stack = arr(Opcodes.INTEGER, Opcodes.LONG); expectedVisitor.visitFrame(Opcodes.F_FULL, 1, arr("Foo"), 2, stack); } /** * Test of ASM * bug: according to JVMS * "4.10.1.9 Type Checking Instructions, AALOAD" resulting type on the * operand stack should be null if the input array is null. */ @Test public void after_aaload_stack_should_contain_null_when_input_array_is_null() { analyzer.visitInsn(Opcodes.ACONST_NULL); analyzer.visitInsn(Opcodes.ICONST_0); analyzer.visitInsn(Opcodes.AALOAD); frame = FrameSnapshot.create(analyzer, 0); final Object[] stack = arr(Opcodes.NULL); expectedVisitor.visitFrame(Opcodes.F_FULL, 1, arr("Foo"), 1, stack); } private Object[] arr(Object... elements) { return elements; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/flow/LabelFlowAnalyzerTest.java000066400000000000000000000252111451257705100324070ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.flow; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertSame; import static org.junit.Assert.assertTrue; import static org.objectweb.asm.Opcodes.*; import org.jacoco.core.data.ExecutionDataWriter; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; /** * Unit tests for {@link LabelFlowAnalyzer}. */ public class LabelFlowAnalyzerTest { private LabelFlowAnalyzer analyzer; private Label label; @Before public void setup() { analyzer = new LabelFlowAnalyzer(); label = new Label(); } @Test public void testInit() { assertFalse(analyzer.successor); assertTrue(analyzer.first); assertNull(analyzer.lineStart); } @Test public void testFlowScenario01() { assertFalse(LabelInfo.isMultiTarget(label)); assertFalse(LabelInfo.isSuccessor(label)); } @Test public void testFlowScenario02() { analyzer.visitJumpInsn(GOTO, label); assertFalse(LabelInfo.isMultiTarget(label)); assertFalse(LabelInfo.isSuccessor(label)); } @Test public void testFlowScenario03() { analyzer.visitInsn(RETURN); analyzer.visitLabel(label); assertFalse(LabelInfo.isMultiTarget(label)); assertFalse(LabelInfo.isSuccessor(label)); } @Test public void testFlowScenario04() { analyzer.visitLabel(label); assertFalse(LabelInfo.isMultiTarget(label)); assertFalse(LabelInfo.isSuccessor(label)); } @Test public void testFlowScenario05() { analyzer.visitLabel(label); analyzer.visitJumpInsn(GOTO, label); assertTrue(LabelInfo.isMultiTarget(label)); assertFalse(LabelInfo.isSuccessor(label)); } @Test public void testFlowScenario06() { analyzer.visitJumpInsn(IFEQ, label); analyzer.visitLabel(label); assertTrue(LabelInfo.isMultiTarget(label)); assertTrue(LabelInfo.isSuccessor(label)); } @Test public void testFlowScenario07() { analyzer.visitJumpInsn(IFEQ, label); analyzer.visitJumpInsn(GOTO, label); assertTrue(LabelInfo.isMultiTarget(label)); assertFalse(LabelInfo.isSuccessor(label)); } @Test public void testFlowScenario08() { analyzer.visitJumpInsn(IFEQ, label); analyzer.visitJumpInsn(IFGT, label); analyzer.visitLabel(label); assertTrue(LabelInfo.isMultiTarget(label)); assertTrue(LabelInfo.isSuccessor(label)); } @Test public void testFlowScenario09() { analyzer.visitInsn(Opcodes.NOP); analyzer.visitLabel(label); analyzer.visitLabel(label); assertFalse(LabelInfo.isMultiTarget(label)); assertTrue(LabelInfo.isSuccessor(label)); } @Test public void testFlowScenario10() { analyzer.visitTryCatchBlock(new Label(), new Label(), label, "java/lang/Exception"); analyzer.visitJumpInsn(GOTO, label); assertTrue(LabelInfo.isMultiTarget(label)); assertFalse(LabelInfo.isSuccessor(label)); } @Test public void testFlowScenario11() { // Even if the same label is referenced multiple times but from the same // source instruction this is only counted as one target. analyzer.visitLookupSwitchInsn(label, new int[] { 0, 1 }, new Label[] { label, label }); assertFalse(LabelInfo.isMultiTarget(label)); assertFalse(LabelInfo.isSuccessor(label)); } @Test public void testFlowScenario12() { // Even if the same label is referenced multiple times but from the same // source instruction this is only counted as one target. analyzer.visitTableSwitchInsn(0, 1, label, new Label[] { label, label }); assertFalse(LabelInfo.isMultiTarget(label)); assertFalse(LabelInfo.isSuccessor(label)); } @Test public void testInsn() { testInsn(NOP, true); testInsn(ACONST_NULL, true); testInsn(ICONST_M1, true); testInsn(ICONST_0, true); testInsn(ICONST_1, true); testInsn(ICONST_2, true); testInsn(ICONST_3, true); testInsn(ICONST_4, true); testInsn(ICONST_5, true); testInsn(LCONST_0, true); testInsn(LCONST_1, true); testInsn(FCONST_0, true); testInsn(FCONST_1, true); testInsn(FCONST_2, true); testInsn(DCONST_0, true); testInsn(DCONST_1, true); testInsn(IALOAD, true); testInsn(LALOAD, true); testInsn(FALOAD, true); testInsn(DALOAD, true); testInsn(AALOAD, true); testInsn(BALOAD, true); testInsn(CALOAD, true); testInsn(SALOAD, true); testInsn(IASTORE, true); testInsn(LASTORE, true); testInsn(FASTORE, true); testInsn(DASTORE, true); testInsn(AASTORE, true); testInsn(BASTORE, true); testInsn(CASTORE, true); testInsn(SASTORE, true); testInsn(POP, true); testInsn(POP2, true); testInsn(DUP, true); testInsn(DUP_X1, true); testInsn(DUP_X2, true); testInsn(DUP2, true); testInsn(DUP2_X1, true); testInsn(DUP2_X2, true); testInsn(SWAP, true); testInsn(IADD, true); testInsn(LADD, true); testInsn(FADD, true); testInsn(DADD, true); testInsn(ISUB, true); testInsn(LSUB, true); testInsn(FSUB, true); testInsn(DSUB, true); testInsn(IMUL, true); testInsn(LMUL, true); testInsn(FMUL, true); testInsn(DMUL, true); testInsn(IDIV, true); testInsn(LDIV, true); testInsn(FDIV, true); testInsn(DDIV, true); testInsn(IREM, true); testInsn(LREM, true); testInsn(FREM, true); testInsn(DREM, true); testInsn(INEG, true); testInsn(LNEG, true); testInsn(FNEG, true); testInsn(DNEG, true); testInsn(ISHL, true); testInsn(LSHL, true); testInsn(ISHR, true); testInsn(LSHR, true); testInsn(IUSHR, true); testInsn(LUSHR, true); testInsn(IAND, true); testInsn(LAND, true); testInsn(IOR, true); testInsn(LOR, true); testInsn(IXOR, true); testInsn(LXOR, true); testInsn(I2L, true); testInsn(I2F, true); testInsn(I2D, true); testInsn(L2I, true); testInsn(L2F, true); testInsn(L2D, true); testInsn(F2I, true); testInsn(F2L, true); testInsn(F2D, true); testInsn(D2I, true); testInsn(D2L, true); testInsn(D2F, true); testInsn(I2B, true); testInsn(I2C, true); testInsn(I2S, true); testInsn(LCMP, true); testInsn(FCMPL, true); testInsn(FCMPG, true); testInsn(DCMPL, true); testInsn(DCMPG, true); testInsn(IRETURN, false); testInsn(LRETURN, false); testInsn(FRETURN, false); testInsn(DRETURN, false); testInsn(ARETURN, false); testInsn(RETURN, false); testInsn(ARRAYLENGTH, true); testInsn(ATHROW, false); testInsn(MONITORENTER, true); testInsn(MONITOREXIT, true); } private void testInsn(int opcode, boolean expected) { // ensure the flags are actually set: analyzer.successor = !expected; analyzer.first = true; analyzer.visitInsn(opcode); assertTrue(expected == analyzer.successor); assertFalse(analyzer.first); } @Test public void testIntInsn() { analyzer.visitIntInsn(BIPUSH, 0); assertTrue(analyzer.successor); assertFalse(analyzer.first); } @Test public void testVarInsn() { analyzer.visitVarInsn(ILOAD, 0); assertTrue(analyzer.successor); assertFalse(analyzer.first); } @Test(expected = AssertionError.class) public void testVisitVarInsnNegative() { analyzer.visitVarInsn(RET, 0); } @Test public void testTypeInsn() { analyzer.visitTypeInsn(NEW, "java/lang/String"); assertTrue(analyzer.successor); assertFalse(analyzer.first); } @Test public void testFieldInsn() { analyzer.successor = false; analyzer.visitFieldInsn(GETFIELD, "Foo", "name", "Ljava/lang/String;"); assertTrue(analyzer.successor); assertFalse(analyzer.first); } @Test public void testLineNumber() { analyzer.visitLineNumber(42, label); assertSame(label, analyzer.lineStart); } /** * @see org.jacoco.core.internal.analysis.MethodAnalyzerTest#zero_line_number_should_create_1_probe() * @see org.jacoco.core.internal.instr.ZeroLineNumberTest */ @Test public void visitLineNumber_should_skip_zero() { analyzer.visitLineNumber(0, label); assertNull(analyzer.lineStart); // workaround for zero line number can be removed if needed // during change of exec file version assertEquals(0x1007, ExecutionDataWriter.FORMAT_VERSION); } @Test public void testMethodInsn() { analyzer.visitLineNumber(42, label); analyzer.visitMethodInsn(INVOKEVIRTUAL, "Foo", "doit", "()V", false); assertTrue(analyzer.successor); assertFalse(analyzer.first); assertTrue(LabelInfo.isMethodInvocationLine(label)); } @Test public void testInvokeDynamicInsn() { analyzer.visitLineNumber(42, label); analyzer.visitInvokeDynamicInsn("foo", "()V", null); assertTrue(analyzer.successor); assertFalse(analyzer.first); assertTrue(LabelInfo.isMethodInvocationLine(label)); } @Test public void testJumpInsn() { testJumpInsn(IFEQ, true); testJumpInsn(IFNE, true); testJumpInsn(IFLT, true); testJumpInsn(IFGE, true); testJumpInsn(IFGT, true); testJumpInsn(IFLE, true); testJumpInsn(IF_ICMPEQ, true); testJumpInsn(IF_ICMPNE, true); testJumpInsn(IF_ICMPLT, true); testJumpInsn(IF_ICMPGE, true); testJumpInsn(IF_ICMPGT, true); testJumpInsn(IF_ICMPLE, true); testJumpInsn(IF_ACMPEQ, true); testJumpInsn(IF_ACMPNE, true); testJumpInsn(GOTO, false); testJumpInsn(IFNULL, true); testJumpInsn(IFNONNULL, true); } private void testJumpInsn(int opcode, boolean expected) { // ensure the flags are actually set: analyzer.successor = !expected; analyzer.first = true; analyzer.visitJumpInsn(opcode, label); assertTrue(expected == analyzer.successor); assertFalse(analyzer.first); } @Test(expected = AssertionError.class) public void testVisitJumpInsnNegative() { analyzer.visitJumpInsn(JSR, label); } @Test public void testLdcInsn() { analyzer.visitLdcInsn("Foo"); assertTrue(analyzer.successor); assertFalse(analyzer.first); } @Test public void testIincInsn() { analyzer.visitIincInsn(0, 1); assertTrue(analyzer.successor); assertFalse(analyzer.first); } @Test public void testTableSwitchInsn() { analyzer.visitTableSwitchInsn(0, 0, label, new Label[] { label }); assertFalse(analyzer.successor); assertFalse(analyzer.first); } @Test public void testLookupSwitchInsn() { analyzer.visitLookupSwitchInsn(label, new int[] { 0 }, new Label[] { label }); assertFalse(analyzer.successor); assertFalse(analyzer.first); } @Test public void testMultiANewArrayInsn() { analyzer.visitMultiANewArrayInsn("java/lang/String", 3); assertTrue(analyzer.successor); assertFalse(analyzer.first); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/flow/LabelInfoTest.java000066400000000000000000000107111451257705100306640ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.flow; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertSame; import static org.junit.Assert.assertTrue; import org.jacoco.core.internal.analysis.Instruction; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.Label; /** * Unit tests for {@link LabelInfoTest}. */ public class LabelInfoTest { private Label label; @Before public void setup() { label = new Label(); } @Test public void testDefaults() { assertFalse(LabelInfo.isMultiTarget(label)); assertFalse(LabelInfo.isSuccessor(label)); assertFalse(LabelInfo.isMethodInvocationLine(label)); assertFalse(LabelInfo.isDone(label)); assertEquals(LabelInfo.NO_PROBE, LabelInfo.getProbeId(label)); assertNull(LabelInfo.getIntermediateLabel(label)); assertNull(LabelInfo.getInstruction(label)); } @Test public void testOtherInfoObject() { label.info = new Object(); assertFalse(LabelInfo.isSuccessor(label)); } @Test public void testSuccessor() { LabelInfo.setSuccessor(label); assertFalse(LabelInfo.isMultiTarget(label)); assertTrue(LabelInfo.isSuccessor(label)); } @Test public void testMultiTarget1() { LabelInfo.setTarget(label); assertFalse(LabelInfo.isMultiTarget(label)); assertFalse(LabelInfo.isSuccessor(label)); LabelInfo.setTarget(label); assertTrue(LabelInfo.isMultiTarget(label)); assertFalse(LabelInfo.isSuccessor(label)); } @Test public void testMultiTarget2() { LabelInfo.setSuccessor(label); assertFalse(LabelInfo.isMultiTarget(label)); assertTrue(LabelInfo.isSuccessor(label)); LabelInfo.setTarget(label); assertTrue(LabelInfo.isMultiTarget(label)); assertTrue(LabelInfo.isSuccessor(label)); } @Test public void testMultiTarget3() { LabelInfo.setTarget(label); assertFalse(LabelInfo.isMultiTarget(label)); assertFalse(LabelInfo.isSuccessor(label)); LabelInfo.setSuccessor(label); assertTrue(LabelInfo.isMultiTarget(label)); assertTrue(LabelInfo.isSuccessor(label)); } @Test public void testMethodInvocationLine() { LabelInfo.setMethodInvocationLine(label); assertTrue(LabelInfo.isMethodInvocationLine(label)); } @Test public void testNeedsProbe() { testNeedsProbe(false, false, false, false); testNeedsProbe(true, false, false, false); testNeedsProbe(false, true, false, false); testNeedsProbe(true, true, false, false); testNeedsProbe(false, false, true, false); testNeedsProbe(true, false, true, true); testNeedsProbe(false, true, true, true); testNeedsProbe(true, true, true, true); } private void testNeedsProbe(boolean multitarget, boolean methodinvocationline, boolean successor, boolean expected) { if (multitarget) { LabelInfo.setTarget(label); LabelInfo.setTarget(label); } if (methodinvocationline) { LabelInfo.setMethodInvocationLine(label); } if (successor) { LabelInfo.setSuccessor(label); } assertTrue(expected == LabelInfo.needsProbe(label)); // Reset: label = new Label(); } @Test public void testSetResetDone1() { LabelInfo.setDone(label); assertTrue(LabelInfo.isDone(label)); LabelInfo.resetDone(label); assertFalse(LabelInfo.isDone(label)); } @Test public void testSetResetDone2() { LabelInfo.setDone(label); assertTrue(LabelInfo.isDone(label)); LabelInfo.resetDone(new Label[] { label, new Label() }); assertFalse(LabelInfo.isDone(label)); } @Test public void testSetProbeId() { LabelInfo.setProbeId(label, 123); assertEquals(123, LabelInfo.getProbeId(label)); } @Test public void testSetIntermediateLabel() { final Label i = new Label(); LabelInfo.setIntermediateLabel(label, i); assertSame(i, LabelInfo.getIntermediateLabel(label)); } @Test public void testSetInstruction() { final Instruction instruction = new Instruction(123); LabelInfo.setInstruction(label, instruction); assertSame(instruction, LabelInfo.getInstruction(label)); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/flow/MethodProbesAdapterTest.java000066400000000000000000000322251451257705100327310ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.flow; import static org.junit.Assert.assertEquals; import java.util.Arrays; import org.jacoco.core.instr.MethodRecorder; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; import org.objectweb.asm.commons.AnalyzerAdapter; import org.objectweb.asm.util.Printer; /** * Unit tests for {@link MethodProbesAdapter}. */ public class MethodProbesAdapterTest implements IProbeIdGenerator { private Label label; private int id; private MethodRecorder expected, actual; private MethodProbesVisitor expectedVisitor; private MethodVisitor adapter; private IFrame frame; private static class TraceAdapter extends MethodProbesVisitor { private final Printer printer; TraceAdapter(MethodRecorder recorder) { super(recorder.getVisitor()); printer = recorder.getPrinter(); } @Override public void visitProbe(int probeId) { rec("visitProbe", Integer.valueOf(probeId)); } @Override public void visitInsnWithProbe(int opcode, int probeId) { rec("visitInsnWithProbe", Integer.valueOf(opcode), Integer.valueOf(probeId)); } @Override public void visitJumpInsnWithProbe(int opcode, Label label, int probeId, IFrame frame) { rec("visitJumpInsnWithProbe", Integer.valueOf(opcode), label, Integer.valueOf(probeId)); frame.accept(this); } @Override public void visitTableSwitchInsnWithProbes(int min, int max, Label dflt, Label[] labels, IFrame frame) { rec("visitTableSwitchInsnWithProbes", Integer.valueOf(min), Integer.valueOf(max), dflt, labels); frame.accept(this); } @Override public void visitLookupSwitchInsnWithProbes(Label dflt, int[] keys, Label[] labels, IFrame frame) { rec("visitLookupSwitchInsnWithProbes", dflt, keys, labels); frame.accept(this); } private void rec(String name, Object... args) { printer.text.add(name + Arrays.asList(args)); } } @Before public void setup() { label = new Label(); id = 1000; expected = new MethodRecorder(); expectedVisitor = new TraceAdapter(expected); actual = new MethodRecorder(); MethodProbesVisitor actualVisitor = new TraceAdapter(actual); MethodProbesAdapter probesAdapter = new MethodProbesAdapter( actualVisitor, this); final AnalyzerAdapter analyzer = new AnalyzerAdapter("Foo", 0, "doit", "()V", probesAdapter); probesAdapter.setAnalyzer(analyzer); adapter = analyzer; frame = new IFrame() { public void accept(MethodVisitor mv) { } }; } @After public void verify() { assertEquals(expected, actual); } @Test public void testVisitProbe1() { LabelInfo.setTarget(label); LabelInfo.setSuccessor(label); adapter.visitLabel(label); expectedVisitor.visitProbe(1000); expectedVisitor.visitLabel(label); } @Test public void testVisitProbe2() { LabelInfo.setTarget(label); LabelInfo.setTarget(label); adapter.visitLabel(label); expectedVisitor.visitLabel(label); } @Test public void testVisitProbe3() { adapter.visitLabel(label); expectedVisitor.visitLabel(label); } @Test public void testVisitInsn1() { adapter.visitInsn(Opcodes.RETURN); expectedVisitor.visitInsnWithProbe(Opcodes.RETURN, 1000); } @Test public void testVisitInsn2() { adapter.visitInsn(Opcodes.ICONST_0); adapter.visitInsn(Opcodes.ICONST_0); adapter.visitInsn(Opcodes.IADD); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitInsn(Opcodes.IADD); } @Test public void testVisitJumpInsn1() { LabelInfo.setTarget(label); LabelInfo.setTarget(label); adapter.visitJumpInsn(Opcodes.GOTO, label); expectedVisitor.visitJumpInsnWithProbe(Opcodes.GOTO, label, 1000, frame); expectedVisitor.visitFrame(Opcodes.F_FULL, 1, new Object[] { "Foo" }, 0, null); } @Test public void testVisitJumpInsn2() { LabelInfo.setTarget(label); LabelInfo.setTarget(label); adapter.visitInsn(Opcodes.ICONST_0); adapter.visitJumpInsn(Opcodes.IFLT, label); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitJumpInsnWithProbe(Opcodes.IFLT, label, 1000, frame); expectedVisitor.visitFrame(Opcodes.F_FULL, 1, new Object[] { "Foo" }, 0, null); } @Test public void testVisitJumpInsn3() { adapter.visitInsn(Opcodes.ICONST_0); adapter.visitJumpInsn(Opcodes.IFLT, label); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitJumpInsn(Opcodes.IFLT, label); } @Test public void testVisitJumpInsn4() { LabelInfo.setTarget(label); LabelInfo.setTarget(label); adapter.visitInsn(Opcodes.ICONST_0); adapter.visitInsn(Opcodes.ICONST_0); adapter.visitJumpInsn(Opcodes.IF_ICMPEQ, label); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitJumpInsnWithProbe(Opcodes.IF_ICMPEQ, label, 1000, frame); expectedVisitor.visitFrame(Opcodes.F_FULL, 1, new Object[] { "Foo" }, 0, null); } @Test public void testVisitLookupSwitchInsn1() { LabelInfo.setTarget(label); LabelInfo.setTarget(label); final int[] keys = new int[] { 0, 1 }; final Label[] labels = new Label[] { label, label }; adapter.visitInsn(Opcodes.ICONST_0); adapter.visitLookupSwitchInsn(label, keys, labels); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitLookupSwitchInsnWithProbes(label, keys, labels, frame); expectedVisitor.visitFrame(Opcodes.F_FULL, 1, new Object[] { "Foo" }, 0, null); assertEquals(1000, LabelInfo.getProbeId(label)); } @Test public void testVisitLookupSwitchInsn2() { Label label2 = new Label(); LabelInfo.setTarget(label2); LabelInfo.setTarget(label2); final int[] keys = new int[] { 0, 1 }; final Label[] labels = new Label[] { label2, label }; adapter.visitInsn(Opcodes.ICONST_0); adapter.visitLookupSwitchInsn(label, keys, labels); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitLookupSwitchInsnWithProbes(label, keys, labels, frame); expectedVisitor.visitFrame(Opcodes.F_FULL, 1, new Object[] { "Foo" }, 0, null); assertEquals(LabelInfo.NO_PROBE, LabelInfo.getProbeId(label)); assertEquals(1000, LabelInfo.getProbeId(label2)); } @Test public void testVisitLookupSwitchInsn3() { final int[] keys = new int[] { 0, 1 }; final Label[] labels = new Label[] { label, label }; adapter.visitInsn(Opcodes.ICONST_0); adapter.visitLookupSwitchInsn(label, keys, labels); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitLookupSwitchInsn(label, keys, labels); } @Test public void testVisitTableSwitchInsn1() { LabelInfo.setTarget(label); LabelInfo.setTarget(label); final Label[] labels = new Label[] { label, label }; adapter.visitInsn(Opcodes.ICONST_0); adapter.visitTableSwitchInsn(0, 1, label, labels); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitTableSwitchInsnWithProbes(0, 1, label, labels, frame); expectedVisitor.visitFrame(Opcodes.F_FULL, 1, new Object[] { "Foo" }, 0, null); assertEquals(1000, LabelInfo.getProbeId(label)); } @Test public void testVisitTableSwitchInsn2() { Label label2 = new Label(); LabelInfo.setTarget(label2); LabelInfo.setTarget(label2); final Label[] labels = new Label[] { label2, label }; adapter.visitInsn(Opcodes.ICONST_0); adapter.visitTableSwitchInsn(0, 1, label, labels); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitTableSwitchInsnWithProbes(0, 1, label, labels, frame); expectedVisitor.visitFrame(Opcodes.F_FULL, 1, new Object[] { "Foo" }, 0, null); assertEquals(LabelInfo.NO_PROBE, LabelInfo.getProbeId(label)); assertEquals(1000, LabelInfo.getProbeId(label2)); } @Test public void testVisitTableSwitchInsn3() { final Label[] labels = new Label[] { label, label }; adapter.visitInsn(Opcodes.ICONST_0); adapter.visitTableSwitchInsn(0, 1, label, labels); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitTableSwitchInsn(0, 1, label, labels); } @Test public void testVisitTryCatchBlockNoProbe() { Label start = new Label(); Label end = new Label(); Label handler = new Label(); adapter.visitTryCatchBlock(start, end, handler, "java/lang/Exception"); adapter.visitLabel(start); adapter.visitInsn(Opcodes.NOP); adapter.visitLabel(end); expectedVisitor.visitTryCatchBlock(start, end, handler, "java/lang/Exception"); expectedVisitor.visitLabel(start); expectedVisitor.visitInsn(Opcodes.NOP); expectedVisitor.visitLabel(end); } @Test public void testVisitTryCatchBlockWithProbeBeforeStart() { Label start = new Label(); LabelInfo.setSuccessor(start); LabelInfo.setTarget(start); Label end = new Label(); Label handler1 = new Label(); Label handler2 = new Label(); adapter.visitTryCatchBlock(start, end, handler1, "java/lang/Exception"); adapter.visitTryCatchBlock(start, end, handler2, "java/lang/Throwable"); adapter.visitLabel(start); adapter.visitInsn(Opcodes.NOP); adapter.visitLabel(end); Label probe = new Label(); expectedVisitor.visitTryCatchBlock(probe, end, handler1, "java/lang/Exception"); expectedVisitor.visitTryCatchBlock(probe, end, handler2, "java/lang/Throwable"); expectedVisitor.visitLabel(probe); expectedVisitor.visitProbe(1000); expectedVisitor.visitLabel(start); expectedVisitor.visitInsn(Opcodes.NOP); expectedVisitor.visitLabel(end); } @Test public void testVisitTryCatchBlockWithProbeBeforeEnd() { Label start = new Label(); Label end = new Label(); LabelInfo.setSuccessor(end); LabelInfo.setTarget(end); Label handler1 = new Label(); Label handler2 = new Label(); adapter.visitTryCatchBlock(start, end, handler1, "java/lang/Exception"); adapter.visitTryCatchBlock(start, end, handler2, "java/lang/Throwable"); adapter.visitLabel(start); adapter.visitInsn(Opcodes.NOP); adapter.visitLabel(end); Label probe = new Label(); expectedVisitor.visitTryCatchBlock(start, probe, handler1, "java/lang/Exception"); expectedVisitor.visitTryCatchBlock(start, probe, handler2, "java/lang/Throwable"); expectedVisitor.visitLabel(start); expectedVisitor.visitInsn(Opcodes.NOP); expectedVisitor.visitLabel(probe); expectedVisitor.visitProbe(1000); expectedVisitor.visitLabel(end); } /** * https://docs.oracle.com/javase/specs/jvms/se9/html/jvms-2.html#jvms-2.11.10 */ @Test public void testStructuredLocking() { Label start = new Label(); LabelInfo.setSuccessor(start); LabelInfo.setTarget(start); Label end = new Label(); LabelInfo.setSuccessor(end); LabelInfo.setTarget(end); Label handlerStart = new Label(); Label handlerEnd = new Label(); Label after = new Label(); adapter.visitTryCatchBlock(start, end, handlerStart, null); adapter.visitTryCatchBlock(handlerStart, handlerEnd, handlerStart, null); adapter.visitVarInsn(Opcodes.ALOAD, 1); adapter.visitInsn(Opcodes.MONITORENTER); adapter.visitLabel(start); adapter.visitInsn(Opcodes.NOP); adapter.visitVarInsn(Opcodes.ALOAD, 1); adapter.visitInsn(Opcodes.MONITOREXIT); adapter.visitLabel(end); adapter.visitJumpInsn(Opcodes.GOTO, after); adapter.visitLabel(handlerStart); adapter.visitVarInsn(Opcodes.ALOAD, 1); adapter.visitInsn(Opcodes.MONITOREXIT); adapter.visitLabel(handlerEnd); adapter.visitInsn(Opcodes.ATHROW); adapter.visitLabel(after); Label probe1 = new Label(); Label probe2 = new Label(); expectedVisitor.visitTryCatchBlock(probe1, probe2, handlerStart, null); expectedVisitor.visitTryCatchBlock(handlerStart, handlerEnd, handlerStart, null); expectedVisitor.visitVarInsn(Opcodes.ALOAD, 1); expectedVisitor.visitInsn(Opcodes.MONITORENTER); // next probe must be INSIDE range of instructions covered by handler, // otherwise monitorexit won't be executed // in case if probe causes exception expectedVisitor.visitLabel(probe1); expectedVisitor.visitProbe(1000); expectedVisitor.visitLabel(start); expectedVisitor.visitInsn(Opcodes.NOP); expectedVisitor.visitVarInsn(Opcodes.ALOAD, 1); expectedVisitor.visitInsn(Opcodes.MONITOREXIT); // next probe must be OUTSIDE range of instructions covered by handler, // otherwise monitorexit will be executed second time // in case if probe causes exception expectedVisitor.visitLabel(probe2); expectedVisitor.visitProbe(1001); expectedVisitor.visitLabel(end); expectedVisitor.visitJumpInsn(Opcodes.GOTO, after); expectedVisitor.visitLabel(handlerStart); expectedVisitor.visitVarInsn(Opcodes.ALOAD, 1); expectedVisitor.visitInsn(Opcodes.MONITOREXIT); expectedVisitor.visitLabel(handlerEnd); expectedVisitor.visitInsnWithProbe(Opcodes.ATHROW, 1002); expectedVisitor.visitLabel(after); } // === IProbeIdGenerator === public int nextId() { return id++; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/flow/MethodSanitizerTest.java000066400000000000000000000074111451257705100321450ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.flow; import static org.junit.Assert.assertEquals; import org.jacoco.core.instr.MethodRecorder; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.MethodNode; /** * Unit tests for {@link MethodSanitizer}. */ public class MethodSanitizerTest { private MethodNode actual; private MethodNode expected; private MethodVisitor sanitizer; @Before public void setup() { actual = new MethodNode(0, "test", "()V", null, null); expected = new MethodNode(0, "test", "()V", null, null); sanitizer = new MethodSanitizer(actual, 0, "test", "()V", null, null); } @Test public void testLocalVariablePositive() { Label l1 = new Label(); Label l2 = new Label(); sanitizer.visitCode(); sanitizer.visitLabel(l1); sanitizer.visitInsn(Opcodes.RETURN); sanitizer.visitLabel(l2); sanitizer.visitLocalVariable("x", "I", null, l1, l2, 0); sanitizer.visitMaxs(0, 0); sanitizer.visitEnd(); Label m1 = new Label(); Label m2 = new Label(); expected.visitLabel(m1); expected.visitInsn(Opcodes.RETURN); expected.visitLabel(m2); expected.visitLocalVariable("x", "I", null, m1, m2, 0); expected.visitMaxs(0, 0); expected.visitEnd(); assertOutput(); } @Test public void testLocalVariableNegative1() { Label l1 = new Label(); Label l2 = new Label(); sanitizer.visitCode(); sanitizer.visitInsn(Opcodes.RETURN); sanitizer.visitLabel(l2); sanitizer.visitLocalVariable("x", "I", null, l1, l2, 0); sanitizer.visitMaxs(0, 0); sanitizer.visitEnd(); Label m2 = new Label(); expected.visitInsn(Opcodes.RETURN); expected.visitLabel(m2); expected.visitMaxs(0, 0); expected.visitEnd(); assertOutput(); } @Test public void testLocalVariableNegative2() { Label l1 = new Label(); Label l2 = new Label(); sanitizer.visitCode(); sanitizer.visitLabel(l1); sanitizer.visitInsn(Opcodes.RETURN); sanitizer.visitLocalVariable("x", "I", null, l1, l2, 0); sanitizer.visitMaxs(0, 0); sanitizer.visitEnd(); Label m1 = new Label(); expected.visitLabel(m1); expected.visitInsn(Opcodes.RETURN); expected.visitMaxs(0, 0); expected.visitEnd(); assertOutput(); } @Test public void testLineNumberPositive() { Label l1 = new Label(); sanitizer.visitCode(); sanitizer.visitLabel(l1); sanitizer.visitLineNumber(15, l1); sanitizer.visitInsn(Opcodes.RETURN); sanitizer.visitMaxs(0, 0); sanitizer.visitEnd(); Label m1 = new Label(); expected.visitLabel(m1); expected.visitLineNumber(15, m1); expected.visitInsn(Opcodes.RETURN); expected.visitMaxs(0, 0); expected.visitEnd(); assertOutput(); } @Test public void testLineNumberNegative() { Label l1 = new Label(); sanitizer.visitCode(); sanitizer.visitLineNumber(15, l1); sanitizer.visitInsn(Opcodes.RETURN); sanitizer.visitMaxs(0, 0); sanitizer.visitEnd(); expected.visitInsn(Opcodes.RETURN); expected.visitMaxs(0, 0); expected.visitEnd(); assertOutput(); } private void assertOutput() { assertEquals(dump(expected), dump(actual)); } private MethodRecorder dump(MethodNode node) { MethodRecorder rec = new MethodRecorder(); node.accept(rec.getVisitor()); return rec; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/instr/000077500000000000000000000000001451257705100255165ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/instr/ClassInstrumenterTest.java000066400000000000000000000040771451257705100327160ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.instr; import static org.junit.Assert.assertNull; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.ClassVisitor; import org.objectweb.asm.MethodVisitor; /** * Unit tests for {@link ClassInstrumenter}. */ public class ClassInstrumenterTest implements IProbeArrayStrategy { private ClassInstrumenter instrumenter; @Before public void setup() { instrumenter = new ClassInstrumenter(this, new ClassVisitor(InstrSupport.ASM_API_VERSION) { }); } @Test(expected = IllegalStateException.class) public void testInstrumentInstrumentedClass1() { instrumenter.visitField(InstrSupport.DATAFIELD_ACC, InstrSupport.DATAFIELD_NAME, InstrSupport.DATAFIELD_DESC, null, null); } @Test(expected = IllegalStateException.class) public void testInstrumentInstrumentedClass2() { instrumenter.visitMethod(InstrSupport.INITMETHOD_ACC, InstrSupport.INITMETHOD_NAME, InstrSupport.INITMETHOD_DESC, null, null); } @Test public void testNoMethodVisitor() { instrumenter = new ClassInstrumenter(this, new ClassVisitor(InstrSupport.ASM_API_VERSION) { @Override public MethodVisitor visitMethod(int access, String name, String desc, String signature, String[] exceptions) { return null; } }); assertNull(instrumenter.visitMethod(0, "foo", "()V", null, null)); } // === IProbeArrayStrategy === public int storeInstance(MethodVisitor mv, boolean clinit, int variable) { return 0; } public void addMembers(ClassVisitor cv, int probeCount) { } } CondyProbeArrayStrategyTest.java000066400000000000000000000063631451257705100337400ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/instr/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.instr; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; import org.jacoco.core.runtime.OfflineInstrumentationAccessGenerator; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.ConstantDynamic; import org.objectweb.asm.Handle; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.ClassNode; import org.objectweb.asm.tree.LdcInsnNode; import org.objectweb.asm.tree.MethodNode; import org.objectweb.asm.tree.TypeInsnNode; import org.objectweb.asm.tree.VarInsnNode; public class CondyProbeArrayStrategyTest { private CondyProbeArrayStrategy strategy; @Before public void setup() { strategy = new CondyProbeArrayStrategy("ClassName", true, 1L, new OfflineInstrumentationAccessGenerator()); } @Test public void should_store_instance_using_condy_and_checkcast() { final MethodNode m = new MethodNode(); final int maxStack = strategy.storeInstance(m, false, 1); assertEquals(1, maxStack); final ConstantDynamic constantDynamic = (ConstantDynamic) ((LdcInsnNode) m.instructions .get(0)).cst; assertEquals("$jacocoData", constantDynamic.getName()); assertEquals("Ljava/lang/Object;", constantDynamic.getDescriptor()); final Handle bootstrapMethod = constantDynamic.getBootstrapMethod(); assertEquals(Opcodes.H_INVOKESTATIC, bootstrapMethod.getTag()); assertEquals("ClassName", bootstrapMethod.getOwner()); assertEquals("$jacocoInit", bootstrapMethod.getName()); assertEquals( "(Ljava/lang/invoke/MethodHandles$Lookup;Ljava/lang/String;Ljava/lang/Class;)[Z", bootstrapMethod.getDesc()); assertTrue(bootstrapMethod.isInterface()); final TypeInsnNode castInstruction = (TypeInsnNode) m.instructions .get(1); assertEquals(Opcodes.CHECKCAST, castInstruction.getOpcode()); assertEquals("[Z", castInstruction.desc); final VarInsnNode storeInstruction = (VarInsnNode) m.instructions .get(2); assertEquals(Opcodes.ASTORE, storeInstruction.getOpcode()); assertEquals(1, storeInstruction.var); assertEquals(3, m.instructions.size()); } @Test public void should_not_add_fields() { final ClassNode c = new ClassNode(); strategy.addMembers(c, 1); assertEquals(0, c.fields.size()); } @Test public void should_add_bootstrap_method() { final ClassNode c = new ClassNode(); strategy.addMembers(c, 1); assertEquals(1, c.methods.size()); final MethodNode m = c.methods.get(0); assertEquals(Opcodes.ACC_SYNTHETIC | Opcodes.ACC_PRIVATE | Opcodes.ACC_STATIC, m.access); assertEquals("$jacocoInit", m.name); assertEquals( "(Ljava/lang/invoke/MethodHandles$Lookup;Ljava/lang/String;Ljava/lang/Class;)[Z", m.desc); assertEquals(4, m.maxStack); assertEquals(3, m.maxLocals); } } DuplicateFrameEliminatorTest.java000066400000000000000000000101141451257705100340500ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/instr/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.instr; import static org.junit.Assert.assertEquals; import org.jacoco.core.instr.MethodRecorder; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.Handle; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.FieldInsnNode; import org.objectweb.asm.tree.IincInsnNode; import org.objectweb.asm.tree.InsnNode; import org.objectweb.asm.tree.IntInsnNode; import org.objectweb.asm.tree.InvokeDynamicInsnNode; import org.objectweb.asm.tree.JumpInsnNode; import org.objectweb.asm.tree.LabelNode; import org.objectweb.asm.tree.LdcInsnNode; import org.objectweb.asm.tree.LookupSwitchInsnNode; import org.objectweb.asm.tree.MethodInsnNode; import org.objectweb.asm.tree.MultiANewArrayInsnNode; import org.objectweb.asm.tree.TableSwitchInsnNode; import org.objectweb.asm.tree.TypeInsnNode; import org.objectweb.asm.tree.VarInsnNode; /** * Unit tests for {@link DuplicateFrameEliminator}. */ public class DuplicateFrameEliminatorTest { private MethodRecorder actual; private MethodRecorder expected; private MethodVisitor eliminator; @Before public void setup() { actual = new MethodRecorder(); expected = new MethodRecorder(); eliminator = new DuplicateFrameEliminator(actual.getVisitor()); } @After public void verify() { assertEquals(expected, actual); } @Test public void testDuplicateFrame() { frame(eliminator); frame(eliminator); frame(expected.getVisitor()); } @Test public void testInsn() { testInstructionBetweenFrames(new InsnNode(Opcodes.NOP)); } @Test public void testIntInsn() { testInstructionBetweenFrames(new IntInsnNode(Opcodes.BIPUSH, 123)); } @Test public void testVarInsn() { testInstructionBetweenFrames(new VarInsnNode(Opcodes.ILOAD, 0)); } @Test public void testTypeInsn() { testInstructionBetweenFrames( new TypeInsnNode(Opcodes.NEW, "java/lang/Object")); } @Test public void testFieldInsn() { testInstructionBetweenFrames( new FieldInsnNode(Opcodes.GETFIELD, "Foo", "f", "I")); } @Test public void testMethodInsn() { testInstructionBetweenFrames(new MethodInsnNode(Opcodes.INVOKEVIRTUAL, "Foo", "run", "()V", false)); } @Test public void testInvokeDynamicInsn() { testInstructionBetweenFrames(new InvokeDynamicInsnNode("foo", "()V", new Handle(Opcodes.H_INVOKEVIRTUAL, null, null, null, false))); } @Test public void testJumpInsn() { testInstructionBetweenFrames( new JumpInsnNode(Opcodes.GOTO, new LabelNode())); } @Test public void testLdcInsn() { testInstructionBetweenFrames(new LdcInsnNode("JaCoCo")); } @Test public void testIincInsn() { testInstructionBetweenFrames(new IincInsnNode(3, 42)); } @Test public void testTableSwitchInsn() { testInstructionBetweenFrames(new TableSwitchInsnNode(0, 0, new LabelNode(), new LabelNode[0])); } @Test public void testLookupSwitchInsn() { testInstructionBetweenFrames(new LookupSwitchInsnNode(new LabelNode(), new int[0], new LabelNode[0])); } @Test public void testMultiANewArrayInsn() { testInstructionBetweenFrames( new MultiANewArrayInsnNode("java/lang/String", 4)); } private void testInstructionBetweenFrames(AbstractInsnNode node) { frame(eliminator); node.accept(eliminator); frame(eliminator); frame(expected.getVisitor()); node.accept(expected.getVisitor()); frame(expected.getVisitor()); } private void frame(MethodVisitor mv) { mv.visitFrame(Opcodes.F_NEW, 1, new Object[] { Opcodes.INTEGER }, 0, new Object[0]); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/instr/InstrSupportTest.java000066400000000000000000000162271451257705100317250ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.instr; import static org.junit.Assert.assertArrayEquals; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.ClassReader; import org.objectweb.asm.ClassVisitor; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.Opcodes; import org.objectweb.asm.util.Printer; import org.objectweb.asm.util.Textifier; import org.objectweb.asm.util.TraceMethodVisitor; /** * Unit tests for {@link InstrSupport}. */ public class InstrSupportTest { private Printer printer; private TraceMethodVisitor trace; @Before public void setup() { printer = new Textifier(); trace = new TraceMethodVisitor(printer); } @Test public void classReaderFor_should_read_java_22_class() { final byte[] bytes = createJava22Class(); final ClassReader classReader = InstrSupport.classReaderFor(bytes); classReader.accept(new ClassVisitor(InstrSupport.ASM_API_VERSION) { @Override public void visit(final int version, final int access, final String name, final String signature, final String superName, final String[] interfaces) { assertEquals(Opcodes.V21 + 1, version); } }, 0); assertArrayEquals(createJava22Class(), bytes); } private static byte[] createJava22Class() { final ClassWriter cw = new ClassWriter(0); cw.visit(Opcodes.V21 + 1, 0, "Foo", null, "java/lang/Object", null); cw.visitEnd(); return cw.toByteArray(); } @Test public void getMajorVersion_should_read_unsigned_two_bytes_at_offset_6() { final byte[] bytes = new byte[] { // (byte) 0xCA, (byte) 0xFE, (byte) 0xBA, (byte) 0xBE, // magic (byte) 0xFF, (byte) 0xFF, // minor_version (byte) 0x80, (byte) 0x12 // major_version }; assertEquals(32786, InstrSupport.getMajorVersion(bytes)); } @Test public void setMajorVersion_should_write_unsigned_two_bytes_at_offset_6() { final byte[] bytes = new byte[8]; InstrSupport.setMajorVersion(32786, bytes); assertArrayEquals( new byte[] { (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, // magic (byte) 0x00, (byte) 0x00, // minor_version (byte) 0x80, (byte) 0x12 // major_version }, bytes); } @Test public void getMajorVersion_should_read_major_version_from_ClassReader_at_offset_relative_to_constant_pool() { final byte[] bytes = new byte[] { // (byte) 0xFF, // before class bytes (byte) 0xCA, (byte) 0xFE, (byte) 0xBA, (byte) 0xBE, // magic 0x00, 0x03, // minor_version (byte) 0x80, 0x12, // major_version 0x00, 0x02, // constant_pool_count 0x01, 0x00, 0x00 // constant_pool }; assertEquals(32786, InstrSupport.getMajorVersion(new ClassReader(bytes, 1, -1))); } @Test public void needFrames_should_return_false_for_versions_less_than_1_6() { assertFalse(InstrSupport.needsFrames(Opcodes.V1_1)); assertFalse(InstrSupport.needsFrames(Opcodes.V1_2)); assertFalse(InstrSupport.needsFrames(Opcodes.V1_3)); assertFalse(InstrSupport.needsFrames(Opcodes.V1_4)); assertFalse(InstrSupport.needsFrames(Opcodes.V1_5)); } @Test public void needFrames_should_return_true_for_versions_greater_than_or_equal_to_1_6() { assertTrue(InstrSupport.needsFrames(Opcodes.V1_6)); assertTrue(InstrSupport.needsFrames(Opcodes.V1_7)); assertTrue(InstrSupport.needsFrames(Opcodes.V1_8)); assertTrue(InstrSupport.needsFrames(Opcodes.V9)); assertTrue(InstrSupport.needsFrames(Opcodes.V10)); assertTrue(InstrSupport.needsFrames(Opcodes.V11)); assertTrue(InstrSupport.needsFrames(Opcodes.V12)); assertTrue(InstrSupport.needsFrames(Opcodes.V13)); assertTrue(InstrSupport.needsFrames(Opcodes.V14)); assertTrue(InstrSupport.needsFrames(Opcodes.V15)); assertTrue(InstrSupport.needsFrames(Opcodes.V16)); assertTrue(InstrSupport.needsFrames(Opcodes.V17)); assertTrue(InstrSupport.needsFrames(Opcodes.V18)); assertTrue(InstrSupport.needsFrames(Opcodes.V19)); assertTrue(InstrSupport.needsFrames(Opcodes.V20)); assertTrue(InstrSupport.needsFrames(Opcodes.V21)); assertTrue(InstrSupport.needsFrames(Opcodes.V21 + 1)); assertTrue(InstrSupport.needsFrames(0x0100)); } @Test public void assertNotIntrumented_should_accept_non_jacoco_memebers() { InstrSupport.assertNotInstrumented("run", "Foo"); } @Test public void assertNotIntrumented_should_throw_exception_when_jacoco_data_field_is_present() { try { InstrSupport.assertNotInstrumented("$jacocoData", "Foo"); fail("exception expected"); } catch (IllegalStateException e) { assertEquals( "Cannot process instrumented class Foo. Please supply original non-instrumented classes.", e.getMessage()); } } @Test public void assertNotIntrumented_should_throw_exception_when_jacoco_init_method_is_present() { try { InstrSupport.assertNotInstrumented("$jacocoInit", "Foo"); fail("exception expected"); } catch (IllegalStateException e) { assertEquals( "Cannot process instrumented class Foo. Please supply original non-instrumented classes.", e.getMessage()); } } @Test public void testPushIntM2147483648() { InstrSupport.push(trace, -2147483648); assertInstruction("LDC -2147483648"); } @Test public void testPushIntM32768() { InstrSupport.push(trace, -32768); assertInstruction("SIPUSH -32768"); } @Test public void testPushIntM128() { InstrSupport.push(trace, -128); assertInstruction("BIPUSH -128"); } @Test public void testPushIntM1() { InstrSupport.push(trace, -1); assertInstruction("ICONST_M1"); } @Test public void testPushInt0() { InstrSupport.push(trace, 0); assertInstruction("ICONST_0"); } @Test public void testPushInt1() { InstrSupport.push(trace, 1); assertInstruction("ICONST_1"); } @Test public void testPushInt2() { InstrSupport.push(trace, 2); assertInstruction("ICONST_2"); } @Test public void testPushInt3() { InstrSupport.push(trace, 3); assertInstruction("ICONST_3"); } @Test public void testPushInt4() { InstrSupport.push(trace, 4); assertInstruction("ICONST_4"); } @Test public void testPushInt5() { InstrSupport.push(trace, 5); assertInstruction("ICONST_5"); } @Test public void testPushInt127() { InstrSupport.push(trace, 127); assertInstruction("BIPUSH 127"); } @Test public void testPushInt32767() { InstrSupport.push(trace, 32767); assertInstruction("SIPUSH 32767"); } @Test public void testPushInt2147483647() { InstrSupport.push(trace, 2147483647); assertInstruction("LDC 2147483647"); } private void assertInstruction(String expected) { assertEquals(1, printer.getText().size()); assertEquals(expected, printer.getText().get(0).toString().trim()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/instr/MethodInstrumenterTest.java000066400000000000000000000151651451257705100330710ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.instr; import static org.junit.Assert.assertEquals; import org.jacoco.core.instr.MethodRecorder; import org.jacoco.core.internal.flow.IFrame; import org.jacoco.core.internal.flow.LabelInfo; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.Label; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; /** * Unit tests for {@link MethodInstrumenter}. */ public class MethodInstrumenterTest { private MethodInstrumenter instrumenter; private MethodRecorder expected, actual; private MethodVisitor expectedVisitor; private IFrame frame; @Before public void setup() { actual = new MethodRecorder(); expected = new MethodRecorder(); expectedVisitor = expected.getVisitor(); final IProbeInserter probeInserter = new IProbeInserter() { public void insertProbe(int id) { actual.getVisitor().visitLdcInsn("Probe " + id); } }; instrumenter = new MethodInstrumenter(actual.getVisitor(), probeInserter); frame = new IFrame() { public void accept(MethodVisitor mv) { mv.visitFrame(Opcodes.F_FULL, 0, null, 0, null); } }; } @Test public void testVisitProbe() { instrumenter.visitProbe(33); expectedVisitor.visitLdcInsn("Probe 33"); assertEquals(expected, actual); } @Test public void testVisitInsnWithProbe() { instrumenter.visitInsnWithProbe(Opcodes.RETURN, 3); expectedVisitor.visitLdcInsn("Probe 3"); expectedVisitor.visitInsn(Opcodes.RETURN); assertEquals(expected, actual); } @Test public void testVisitJumpInsnWithProbe_GOTO() { final Label label = new Label(); instrumenter.visitJumpInsnWithProbe(Opcodes.GOTO, label, 3, frame); expectedVisitor.visitLdcInsn("Probe 3"); expectedVisitor.visitJumpInsn(Opcodes.GOTO, label); assertEquals(expected, actual); } @Test public void testVisitJumpInsnWithProbe_IFEQ() { testVisitJumpInsnWithProbe(Opcodes.IFEQ, Opcodes.IFNE); } @Test public void testVisitJumpInsnWithProbe_IFGE() { testVisitJumpInsnWithProbe(Opcodes.IFGE, Opcodes.IFLT); } @Test public void testVisitJumpInsnWithProbe_IFGT() { testVisitJumpInsnWithProbe(Opcodes.IFGT, Opcodes.IFLE); } @Test public void testVisitJumpInsnWithProbe_IFLE() { testVisitJumpInsnWithProbe(Opcodes.IFLE, Opcodes.IFGT); } @Test public void testVisitJumpInsnWithProbe_IFLT() { testVisitJumpInsnWithProbe(Opcodes.IFLT, Opcodes.IFGE); } @Test public void testVisitJumpInsnWithProbe_IFNE() { testVisitJumpInsnWithProbe(Opcodes.IFNE, Opcodes.IFEQ); } @Test public void testVisitJumpInsnWithProbe_IF_ACMPEQ() { testVisitJumpInsnWithProbe(Opcodes.IF_ACMPEQ, Opcodes.IF_ACMPNE); } @Test public void testVisitJumpInsnWithProbe_IF_ACMPNE() { testVisitJumpInsnWithProbe(Opcodes.IF_ACMPNE, Opcodes.IF_ACMPEQ); } @Test public void testVisitJumpInsnWithProbe_IF_ICMPEQ() { testVisitJumpInsnWithProbe(Opcodes.IF_ICMPEQ, Opcodes.IF_ICMPNE); } @Test public void testVisitJumpInsnWithProbe_IF_ICMPGE() { testVisitJumpInsnWithProbe(Opcodes.IF_ICMPGE, Opcodes.IF_ICMPLT); } @Test public void testVisitJumpInsnWithProbe_IF_ICMPGT() { testVisitJumpInsnWithProbe(Opcodes.IF_ICMPGT, Opcodes.IF_ICMPLE); } @Test public void testVisitJumpInsnWithProbe_IF_ICMPLE() { testVisitJumpInsnWithProbe(Opcodes.IF_ICMPLE, Opcodes.IF_ICMPGT); } @Test public void testVisitJumpInsnWithProbe_IF_ICMPLT() { testVisitJumpInsnWithProbe(Opcodes.IF_ICMPLT, Opcodes.IF_ICMPGE); } @Test public void testVisitJumpInsnWithProbe_IF_ICMPNE() { testVisitJumpInsnWithProbe(Opcodes.IF_ICMPNE, Opcodes.IF_ICMPEQ); } @Test public void testVisitJumpInsnWithProbe_IFNULL() { testVisitJumpInsnWithProbe(Opcodes.IFNULL, Opcodes.IFNONNULL); } @Test public void testVisitJumpInsnWithProbe_IFNONNULL() { testVisitJumpInsnWithProbe(Opcodes.IFNONNULL, Opcodes.IFNULL); } @Test(expected = IllegalArgumentException.class) public void testVisitJumpInsnWithProbe_InvalidOpcode() { testVisitJumpInsnWithProbe(Opcodes.NOP, Opcodes.NOP); } private void testVisitJumpInsnWithProbe(int opcodeOrig, int opcodeInstr) { final Label label = new Label(); instrumenter.visitJumpInsnWithProbe(opcodeOrig, label, 3, frame); final Label l2 = new Label(); expectedVisitor.visitJumpInsn(opcodeInstr, l2); expectedVisitor.visitLdcInsn("Probe 3"); expectedVisitor.visitJumpInsn(Opcodes.GOTO, label); expectedVisitor.visitLabel(l2); expectedVisitor.visitFrame(Opcodes.F_FULL, 0, null, 0, null); assertEquals(expected, actual); } @Test public void testVisitTableSwitchInsnWithProbes() { final Label L0 = new Label(); final Label L1 = new Label(); final Label L2 = new Label(); LabelInfo.setProbeId(L0, 0); LabelInfo.setProbeId(L1, 1); instrumenter.visitTableSwitchInsnWithProbes(3, 5, L0, new Label[] { L1, L1, L2 }, frame); expectedVisitor.visitTableSwitchInsn(3, 4, L0, new Label[] { L1, L1, L2 }); expectedVisitor.visitLabel(L0); expectedVisitor.visitFrame(Opcodes.F_FULL, 0, null, 0, null); expectedVisitor.visitLdcInsn("Probe 0"); expectedVisitor.visitJumpInsn(Opcodes.GOTO, new Label()); expectedVisitor.visitLabel(L1); expectedVisitor.visitFrame(Opcodes.F_FULL, 0, null, 0, null); expectedVisitor.visitLdcInsn("Probe 1"); expectedVisitor.visitJumpInsn(Opcodes.GOTO, new Label()); assertEquals(expected, actual); } @Test public void testVisitLookupSwitchInsnWithProbes() { final Label L0 = new Label(); final Label L1 = new Label(); final Label L2 = new Label(); LabelInfo.setProbeId(L0, 0); LabelInfo.setProbeId(L1, 1); instrumenter.visitLookupSwitchInsnWithProbes(L0, new int[] { 10, 20, 30 }, new Label[] { L1, L1, L2 }, frame); expectedVisitor.visitLookupSwitchInsn(L0, new int[] { 10, 20, 30 }, new Label[] { L1, L1, L2 }); expectedVisitor.visitLabel(L0); expectedVisitor.visitFrame(Opcodes.F_FULL, 0, null, 0, null); expectedVisitor.visitLdcInsn("Probe 0"); expectedVisitor.visitJumpInsn(Opcodes.GOTO, new Label()); expectedVisitor.visitLabel(L1); expectedVisitor.visitFrame(Opcodes.F_FULL, 0, null, 0, null); expectedVisitor.visitLdcInsn("Probe 1"); expectedVisitor.visitJumpInsn(Opcodes.GOTO, new Label()); assertEquals(expected, actual); } } NoneProbeArrayStrategyTest.java000066400000000000000000000024441451257705100335570ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/instr/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.instr; import static org.junit.Assert.assertEquals; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.tree.ClassNode; /** * Unit tests for {@link NoneProbeArrayStrategy}. */ public class NoneProbeArrayStrategyTest { private NoneProbeArrayStrategy strategy; @Before public void setup() { strategy = new NoneProbeArrayStrategy(); } @Test(expected = UnsupportedOperationException.class) public void storeInstance_should_throw_UnsupportedOperationException() { strategy.storeInstance(null, false, 0); } @Test public void addMembers_should_not_add_members() { final ClassNode c = new ClassNode(); strategy.addMembers(c, 0); assertEquals(0, c.methods.size()); assertEquals(0, c.fields.size()); } } ProbeArrayStrategyFactoryTest.java000066400000000000000000000321411451257705100342640ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/instr/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.instr; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNull; import static org.junit.Assert.fail; import java.util.ArrayList; import java.util.List; import org.jacoco.core.runtime.IExecutionDataAccessorGenerator; import org.jacoco.core.runtime.OfflineInstrumentationAccessGenerator; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.ClassReader; import org.objectweb.asm.ClassVisitor; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.FieldVisitor; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; /** * Unit tests for {@link ProbeArrayStrategyFactory} and the * {@link IProbeArrayStrategy} implementations. The verifies the behaviour of * the returned {@link IProbeArrayStrategy} instances for different classes. */ public class ProbeArrayStrategyFactoryTest { private IExecutionDataAccessorGenerator generator; private ClassVisitorMock cv; @Before public void setup() { generator = new OfflineInstrumentationAccessGenerator(); cv = new ClassVisitorMock(); } @Test public void testClass1() { final IProbeArrayStrategy strategy = test(Opcodes.V1_1, 0, false, true, true); assertEquals(ClassFieldProbeArrayStrategy.class, strategy.getClass()); assertDataField(InstrSupport.DATAFIELD_ACC); assertInitMethod(false); } @Test public void testClass2() { final IProbeArrayStrategy strategy = test(Opcodes.V1_2, 0, false, true, true); assertEquals(ClassFieldProbeArrayStrategy.class, strategy.getClass()); assertDataField(InstrSupport.DATAFIELD_ACC); assertInitMethod(false); } @Test public void testClass3() { final IProbeArrayStrategy strategy = test(Opcodes.V1_3, 0, false, true, true); assertEquals(ClassFieldProbeArrayStrategy.class, strategy.getClass()); assertDataField(InstrSupport.DATAFIELD_ACC); assertInitMethod(false); } @Test public void testClass4() { final IProbeArrayStrategy strategy = test(Opcodes.V1_4, 0, false, true, true); assertEquals(ClassFieldProbeArrayStrategy.class, strategy.getClass()); assertDataField(InstrSupport.DATAFIELD_ACC); assertInitMethod(false); } @Test public void testClass5() { final IProbeArrayStrategy strategy = test(Opcodes.V1_5, 0, false, true, true); assertEquals(ClassFieldProbeArrayStrategy.class, strategy.getClass()); assertDataField(InstrSupport.DATAFIELD_ACC); assertInitMethod(false); } @Test public void testClass6() { final IProbeArrayStrategy strategy = test(Opcodes.V1_6, 0, false, true, true); assertEquals(ClassFieldProbeArrayStrategy.class, strategy.getClass()); assertDataField(InstrSupport.DATAFIELD_ACC); assertInitMethod(true); } @Test public void testClass7() { final IProbeArrayStrategy strategy = test(Opcodes.V1_7, 0, false, true, true); assertEquals(ClassFieldProbeArrayStrategy.class, strategy.getClass()); assertDataField(InstrSupport.DATAFIELD_ACC); assertInitMethod(true); } @Test public void testClass8() { final IProbeArrayStrategy strategy = test(Opcodes.V1_8, 0, false, true, true); assertEquals(ClassFieldProbeArrayStrategy.class, strategy.getClass()); assertDataField(InstrSupport.DATAFIELD_ACC); assertInitMethod(true); strategy.storeInstance(cv.visitMethod(0, null, null, null, null), false, 0); } @Test public void testInterface7() { final IProbeArrayStrategy strategy = test(Opcodes.V1_7, Opcodes.ACC_INTERFACE, true, false, true); assertEquals(LocalProbeArrayStrategy.class, strategy.getClass()); assertNoDataField(); assertNoInitMethod(); } @Test public void testEmptyInterface7() { final IProbeArrayStrategy strategy = test(Opcodes.V1_7, Opcodes.ACC_INTERFACE, false, false, false); assertEquals(NoneProbeArrayStrategy.class, strategy.getClass()); assertNoDataField(); assertNoInitMethod(); } @Test(expected = UnsupportedOperationException.class) public void testEmptyInterface7StoreInstance() { IProbeArrayStrategy strategy = test(Opcodes.V1_7, Opcodes.ACC_INTERFACE, false, false, false); strategy.storeInstance(null, false, 0); } @Test public void testInterface8() { cv.isInterface = true; final IProbeArrayStrategy strategy = test(Opcodes.V1_8, Opcodes.ACC_INTERFACE, false, true, true); assertEquals(InterfaceFieldProbeArrayStrategy.class, strategy.getClass()); assertDataField(InstrSupport.DATAFIELD_INTF_ACC); assertInitAndClinitMethods(); strategy.storeInstance(cv.visitMethod(0, null, null, null, null), false, 0); } @Test public void testEmptyInterface8() { final IProbeArrayStrategy strategy = test(Opcodes.V1_8, Opcodes.ACC_INTERFACE, false, false, false); assertEquals(NoneProbeArrayStrategy.class, strategy.getClass()); assertNoDataField(); assertNoInitMethod(); } @Test(expected = UnsupportedOperationException.class) public void testEmptyInterface8StoreInstance() { final IProbeArrayStrategy strategy = test(Opcodes.V1_8, Opcodes.ACC_INTERFACE, false, false, false); strategy.storeInstance(null, false, 0); } @Test public void testClinitAndAbstractMethodsInterface8() { final IProbeArrayStrategy strategy = test(Opcodes.V1_8, Opcodes.ACC_INTERFACE, true, false, true); assertEquals(LocalProbeArrayStrategy.class, strategy.getClass()); assertNoDataField(); assertNoInitMethod(); strategy.storeInstance(cv.visitMethod(0, null, null, null, null), false, 0); } @Test public void testClinitInterface8() { final IProbeArrayStrategy strategy = test(Opcodes.V1_8, Opcodes.ACC_INTERFACE, true, false, false); assertEquals(LocalProbeArrayStrategy.class, strategy.getClass()); assertNoDataField(); assertNoInitMethod(); } @Test public void testClinitAndMethodsInterface8() { cv.isInterface = true; final IProbeArrayStrategy strategy = test(Opcodes.V1_8, Opcodes.ACC_INTERFACE, true, true, true); assertEquals(InterfaceFieldProbeArrayStrategy.class, strategy.getClass()); assertDataField(InstrSupport.DATAFIELD_INTF_ACC); assertInitAndClinitMethods(); strategy.storeInstance(cv.visitMethod(0, "", null, null, null), true, 0); } @Test public void test_java9_module() { final IProbeArrayStrategy strategy = createForModule(Opcodes.V9); assertEquals(NoneProbeArrayStrategy.class, strategy.getClass()); } @Test public void test_java11_class() { final IProbeArrayStrategy strategy = test(Opcodes.V11, 0, true, true, true); assertEquals(CondyProbeArrayStrategy.class, strategy.getClass()); assertNoDataField(); assertCondyBootstrapMethod(); } @Test public void test_java11_interface_with_clinit_and_methods() { final IProbeArrayStrategy strategy = test(Opcodes.V11, Opcodes.ACC_INTERFACE, true, true, true); assertEquals(CondyProbeArrayStrategy.class, strategy.getClass()); assertNoDataField(); assertCondyBootstrapMethod(); } @Test public void test_java11_interface_with_clinit() { final IProbeArrayStrategy strategy = test(Opcodes.V11, Opcodes.ACC_INTERFACE, true, false, true); assertEquals(LocalProbeArrayStrategy.class, strategy.getClass()); assertNoDataField(); assertNoInitMethod(); } @Test public void test_java11_interface_without_code() { final IProbeArrayStrategy strategy = test(Opcodes.V11, Opcodes.ACC_INTERFACE, false, false, true); assertEquals(NoneProbeArrayStrategy.class, strategy.getClass()); assertNoDataField(); assertNoInitMethod(); } @Test public void test_java11_module() { final IProbeArrayStrategy strategy = createForModule(Opcodes.V11); assertEquals(NoneProbeArrayStrategy.class, strategy.getClass()); } private IProbeArrayStrategy createForModule(int version) { final ClassWriter writer = new ClassWriter(0); writer.visit(version, Opcodes.ACC_MODULE, "module-info", null, null, null); writer.visitModule("module", 0, null).visitEnd(); writer.visitEnd(); return ProbeArrayStrategyFactory.createFor(0, new ClassReader(writer.toByteArray()), generator); } private IProbeArrayStrategy test(int version, int access, boolean clinit, boolean method, boolean abstractMethod) { final ClassWriter writer = new ClassWriter(0); writer.visit(version, access, "Foo", "java/lang/Object", null, null); if (clinit) { final MethodVisitor mv = writer.visitMethod( Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC, "", "()V", null, null); mv.visitCode(); mv.visitInsn(Opcodes.RETURN); mv.visitMaxs(0, 0); mv.visitEnd(); } if (method) { final MethodVisitor mv = writer.visitMethod( Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC, "doit", "()V", null, null); mv.visitCode(); mv.visitInsn(Opcodes.RETURN); mv.visitMaxs(0, 0); mv.visitEnd(); } if (abstractMethod) { final MethodVisitor mv = writer.visitMethod(Opcodes.ACC_ABSTRACT, "foo", "()V", null, null); mv.visitEnd(); } writer.visitEnd(); final IProbeArrayStrategy strategy = ProbeArrayStrategyFactory .createFor(0, new ClassReader(writer.toByteArray()), generator); strategy.addMembers(cv, 123); return strategy; } private static class AddedMethod { private final int access; private final String name; private final String desc; private boolean frames; AddedMethod(int access, String name, String desc) { this.access = access; this.name = name; this.desc = desc; } void assertInitMethod(String expectedDesc, boolean frames) { assertEquals(InstrSupport.INITMETHOD_NAME, name); assertEquals(expectedDesc, desc); assertEquals(InstrSupport.INITMETHOD_ACC, access); assertEquals(Boolean.valueOf(frames), Boolean.valueOf(frames)); } void assertClinit() { assertEquals(InstrSupport.CLINIT_NAME, name); assertEquals(InstrSupport.CLINIT_DESC, desc); assertEquals(InstrSupport.CLINIT_ACC, access); assertEquals(Boolean.valueOf(false), Boolean.valueOf(frames)); } } private static class ClassVisitorMock extends ClassVisitor { private boolean isInterface; private int fieldAccess; private String fieldName; private final List methods = new ArrayList(); ClassVisitorMock() { super(InstrSupport.ASM_API_VERSION); } @Override public FieldVisitor visitField(int access, String name, String desc, String signature, Object value) { assertNull(fieldName); fieldAccess = access; fieldName = name; return null; } @Override public MethodVisitor visitMethod(int access, String name, String desc, String signature, String[] exceptions) { final AddedMethod m = new AddedMethod(access, name, desc); methods.add(m); return new MethodVisitor(InstrSupport.ASM_API_VERSION) { @Override public void visitFrame(int type, int nLocal, Object[] local, int nStack, Object[] stack) { m.frames = true; } @Override public void visitFieldInsn(int opcode, String owner, String name, String desc) { assertEquals(InstrSupport.DATAFIELD_NAME, name); assertEquals(InstrSupport.DATAFIELD_DESC, desc); if (opcode == Opcodes.GETSTATIC) { assertEquals(InstrSupport.INITMETHOD_NAME, methods.get(methods.size() - 1).name); } else if (opcode == Opcodes.PUTSTATIC) { if (isInterface) { assertEquals(InstrSupport.CLINIT_NAME, methods.get(methods.size() - 1).name); } else { assertEquals(InstrSupport.INITMETHOD_NAME, methods.get(methods.size() - 1).name); } } else { fail(); } } @Override public void visitMethodInsn(int opcode, String owner, String name, String desc, boolean itf) { if ("getProbes".equals(name)) { // method's owner is not interface: assertFalse(itf); return; } assertEquals(Boolean.valueOf(itf), Boolean.valueOf(isInterface)); assertEquals(Opcodes.INVOKESTATIC, opcode); assertEquals("Foo", owner); assertEquals(InstrSupport.INITMETHOD_NAME, name); assertEquals(InstrSupport.INITMETHOD_DESC, desc); } }; } } void assertDataField(int access) { assertEquals(InstrSupport.DATAFIELD_NAME, cv.fieldName); assertEquals(access, cv.fieldAccess); } void assertNoDataField() { assertNull(cv.fieldName); } void assertInitMethod(boolean frames) { assertEquals(cv.methods.size(), 1); cv.methods.get(0).assertInitMethod(InstrSupport.INITMETHOD_DESC, frames); } void assertCondyBootstrapMethod() { assertEquals(cv.methods.size(), 1); cv.methods.get(0).assertInitMethod(CondyProbeArrayStrategy.B_DESC, false); } void assertInitAndClinitMethods() { assertEquals(2, cv.methods.size()); cv.methods.get(0).assertInitMethod(InstrSupport.INITMETHOD_DESC, true); cv.methods.get(1).assertClinit(); } void assertNoInitMethod() { assertEquals(0, cv.methods.size()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/instr/ProbeCounterTest.java000066400000000000000000000032701451257705100316320ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.instr; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.Opcodes; /** * Unit tests for {@link ProbeCounter}. */ public class ProbeCounterTest { private ProbeCounter counter; @Before public void setup() { counter = new ProbeCounter(); } @Test public void testInitial() { assertFalse(counter.hasMethods()); assertEquals(0, counter.getCount()); } @Test public void testVisitTotalProbeCount() { counter.visitTotalProbeCount(42); assertEquals(42, counter.getCount()); } @Test public void testVisitClinitMethod() { assertNull(counter.visitMethod(0, "", null, null, null)); assertFalse(counter.hasMethods()); } @Test public void testVisitAbstractMethod() { counter.visitMethod(Opcodes.ACC_ABSTRACT, "foo", null, null, null); assertFalse(counter.hasMethods()); } @Test public void testVisitMethod() { assertNull(counter.visitMethod(0, "foo", null, null, null)); assertTrue(counter.hasMethods()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/instr/ProbeInserterTest.java000066400000000000000000000273041451257705100320120ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.instr; import static org.junit.Assert.assertEquals; import org.jacoco.core.instr.MethodRecorder; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.ClassVisitor; import org.objectweb.asm.Label; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; import org.objectweb.asm.TypeReference; /** * Unit tests for {@link ProbeInserter}. */ public class ProbeInserterTest { private MethodRecorder actual, expected; private MethodVisitor actualVisitor, expectedVisitor; private IProbeArrayStrategy arrayStrategy; @Before public void setup() { actual = new MethodRecorder(); actualVisitor = actual.getVisitor(); expected = new MethodRecorder(); expectedVisitor = expected.getVisitor(); arrayStrategy = new IProbeArrayStrategy() { public int storeInstance(MethodVisitor mv, boolean clinit, int variable) { mv.visitLdcInsn(clinit ? "clinit" : "init"); return 5; } public void addMembers(ClassVisitor delegate, int probeCount) { } }; } @After public void verify() { assertEquals(expected, actual); } @Test public void probevar_should_be_at_position_1_for_static_method_without_parameters() { ProbeInserter pi = new ProbeInserter(Opcodes.ACC_STATIC, "m", "()V", actualVisitor, arrayStrategy); pi.insertProbe(0); expectedVisitor.visitVarInsn(Opcodes.ALOAD, 1); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitInsn(Opcodes.ICONST_1); expectedVisitor.visitInsn(Opcodes.BASTORE); } @Test public void probevar_should_be_at_position_2_for_instance_method_without_parameters() { ProbeInserter pi = new ProbeInserter(0, "m", "()V", actualVisitor, arrayStrategy); pi.insertProbe(0); expectedVisitor.visitVarInsn(Opcodes.ALOAD, 2); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitInsn(Opcodes.ICONST_1); expectedVisitor.visitInsn(Opcodes.BASTORE); } @Test public void probevar_should_be_at_position_5_for_instance_method_with_3_parameters() { ProbeInserter pi = new ProbeInserter(0, "m", "(IZLjava/lang/Object;)V", actualVisitor, arrayStrategy); pi.insertProbe(0); expectedVisitor.visitVarInsn(Opcodes.ALOAD, 5); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitInsn(Opcodes.ICONST_1); expectedVisitor.visitInsn(Opcodes.BASTORE); } @Test public void probevar_should_be_at_position_6_for_instance_method_with_2_wide_parameters() { ProbeInserter pi = new ProbeInserter(0, "m", "(JD)V", actualVisitor, arrayStrategy); pi.insertProbe(0); expectedVisitor.visitVarInsn(Opcodes.ALOAD, 6); expectedVisitor.visitInsn(Opcodes.ICONST_0); expectedVisitor.visitInsn(Opcodes.ICONST_1); expectedVisitor.visitInsn(Opcodes.BASTORE); } @Test public void visitCode_should_call_IProbeArrayStrategy_for_any_methods() { ProbeInserter pi = new ProbeInserter(0, "m", "()V", actualVisitor, arrayStrategy); pi.visitCode(); expectedVisitor.visitLabel(new Label()); expectedVisitor.visitLdcInsn("init"); } @Test public void visitCode_should_call_IProbeArrayStrategy_for_static_initializers() { ProbeInserter pi = new ProbeInserter(0, "", "()V", actualVisitor, arrayStrategy); pi.visitCode(); expectedVisitor.visitLabel(new Label()); expectedVisitor.visitLdcInsn("clinit"); } @Test public void visitVarInsn_should_be_called_with_adjusted_variable_positions() { ProbeInserter pi = new ProbeInserter(0, "m", "(II)V", actualVisitor, arrayStrategy); pi.visitVarInsn(Opcodes.ALOAD, 0); pi.visitVarInsn(Opcodes.ILOAD, 1); pi.visitVarInsn(Opcodes.ILOAD, 2); pi.visitVarInsn(Opcodes.ISTORE, 3); pi.visitVarInsn(Opcodes.FSTORE, 4); // Argument variables stay at the same position: expectedVisitor.visitVarInsn(Opcodes.ALOAD, 0); expectedVisitor.visitVarInsn(Opcodes.ILOAD, 1); expectedVisitor.visitVarInsn(Opcodes.ILOAD, 2); // Local variables are shifted by two: expectedVisitor.visitVarInsn(Opcodes.ISTORE, 5); expectedVisitor.visitVarInsn(Opcodes.FSTORE, 6); } @Test public void visitIincInsn_should_be_called_with_adjusted_variable_positions() { ProbeInserter pi = new ProbeInserter(0, "m", "(II)V", actualVisitor, arrayStrategy); pi.visitIincInsn(0, 100); pi.visitIincInsn(1, 101); pi.visitIincInsn(2, 102); pi.visitIincInsn(3, 103); pi.visitIincInsn(4, 104); // Argument variables stay at the same position: expectedVisitor.visitIincInsn(0, 100); expectedVisitor.visitIincInsn(1, 101); expectedVisitor.visitIincInsn(2, 102); // Local variables are shifted by two: expectedVisitor.visitIincInsn(5, 103); expectedVisitor.visitIincInsn(6, 104); } @Test public void visitLocalVariable_should_be_called_with_adjusted_variable_positions() { ProbeInserter pi = new ProbeInserter(0, "m", "(II)V", actualVisitor, arrayStrategy); pi.visitLocalVariable(null, null, null, null, null, 0); pi.visitLocalVariable(null, null, null, null, null, 1); pi.visitLocalVariable(null, null, null, null, null, 2); pi.visitLocalVariable(null, null, null, null, null, 3); pi.visitLocalVariable(null, null, null, null, null, 4); Label begin = new Label(); // Argument variables stay at the same position: expectedVisitor.visitLocalVariable(null, null, null, begin, null, 0); expectedVisitor.visitLocalVariable(null, null, null, begin, null, 1); expectedVisitor.visitLocalVariable(null, null, null, begin, null, 2); // Local variables are shifted by two: expectedVisitor.visitLocalVariable(null, null, null, null, null, 5); expectedVisitor.visitLocalVariable(null, null, null, null, null, 6); } @Test public void should_remap_LocalVariableAnnotation() { ProbeInserter pi = new ProbeInserter(0, "m", "(I)V", actualVisitor, arrayStrategy); final Label start = new Label(); pi.visitLabel(start); final Label end = new Label(); pi.visitLabel(end); pi.visitLocalVariableAnnotation(TypeReference.LOCAL_VARIABLE, null, new Label[] { start }, new Label[] { end }, new int[] { 2 }, "LNonNull;", false); expectedVisitor.visitLabel(start); expectedVisitor.visitLabel(end); // Local variables are shifted by two: expectedVisitor.visitLocalVariableAnnotation( TypeReference.LOCAL_VARIABLE, null, new Label[] { start }, new Label[] { end }, new int[] { 4 }, "LNonNull;", false); } @Test public void new_stack_size_should_be_big_enought_to_store_probe_array() { ProbeInserter pi = new ProbeInserter(0, "m", "(II)V", actualVisitor, arrayStrategy); pi.visitCode(); pi.visitMaxs(0, 8); expectedVisitor.visitLabel(new Label()); expectedVisitor.visitLdcInsn("init"); expectedVisitor.visitMaxs(5, 10); } @Test public void new_stack_size_should_be_increased_for_probes() { ProbeInserter pi = new ProbeInserter(0, "m", "(II)V", actualVisitor, arrayStrategy); pi.visitCode(); pi.visitMaxs(10, 8); expectedVisitor.visitLabel(new Label()); expectedVisitor.visitLdcInsn("init"); expectedVisitor.visitMaxs(13, 10); } @Test public void visitFrame_should_insert_safety_slot_and_probe_variable_between_arguments_and_local_variables() { ProbeInserter pi = new ProbeInserter(0, "m", "(J)V", actualVisitor, arrayStrategy); pi.visitFrame(Opcodes.F_NEW, 3, new Object[] { "Foo", Opcodes.LONG, "java/lang/String" }, 0, new Object[0]); expectedVisitor.visitFrame(Opcodes.F_NEW, 5, new Object[] { // "Foo", // Opcodes.LONG, // Opcodes.TOP, // safety slot "[Z", // probe array "java/lang/String" // }, 0, new Object[0]); } @Test public void visitFrame_should_only_insert_safety_slot_and_probe_variable_when_no_other_local_variables_exist() { ProbeInserter pi = new ProbeInserter(Opcodes.ACC_STATIC, "m", "()V", actualVisitor, arrayStrategy); pi.visitFrame(Opcodes.F_NEW, 0, new Object[] {}, 0, new Object[0]); expectedVisitor.visitFrame(Opcodes.F_NEW, 2, new Object[] { // Opcodes.TOP, // safety slot "[Z", // probe array }, 0, new Object[0]); } @Test public void visitFrame_should_insert_safety_slot_and_probe_variable_first_when_no_parameters_exist() { ProbeInserter pi = new ProbeInserter(Opcodes.ACC_STATIC, "m", "()V", actualVisitor, arrayStrategy); pi.visitFrame(Opcodes.F_NEW, 2, new Object[] { Opcodes.DOUBLE, "Foo" }, 0, new Object[0]); expectedVisitor.visitFrame(Opcodes.F_NEW, 4, new Object[] { // Opcodes.TOP, // safety slot "[Z", // probe array Opcodes.DOUBLE, // "Foo" // }, 0, new Object[0]); } @Test public void visitFrame_should_fill_2_unused_slots_before_probe_variable_with_TOP_TOP() { ProbeInserter pi = new ProbeInserter(Opcodes.ACC_STATIC, "m", "(I)V", actualVisitor, arrayStrategy); pi.visitFrame(Opcodes.F_NEW, 0, new Object[] {}, 0, new Object[] {}); // The locals in this frame are filled with TOP up to the probe variable expectedVisitor.visitFrame(Opcodes.F_NEW, 3, new Object[] { // Opcodes.TOP, // Opcodes.TOP, // safety slot "[Z", // probe array }, 0, new Object[] {}); } @Test public void visitFrame_should_fill_3_unused_slots_before_probe_variable_with_TOP_TOP_TOP() { ProbeInserter pi = new ProbeInserter(Opcodes.ACC_STATIC, "m", "(J)V", actualVisitor, arrayStrategy); pi.visitFrame(Opcodes.F_NEW, 0, new Object[] {}, 0, new Object[] {}); // The locals in this frame are filled with TOP up to the probe variable expectedVisitor.visitFrame(Opcodes.F_NEW, 4, new Object[] { // Opcodes.TOP, // Opcodes.TOP, // Opcodes.TOP, // safety slot "[Z", // probe array }, 0, new Object[] {}); } @Test public void visitFrame_should_fill_4_unused_slots_before_probe_variable_with_TOP_TOP_TOP_TOP() { ProbeInserter pi = new ProbeInserter(Opcodes.ACC_STATIC, "m", "(DIJ)V", actualVisitor, arrayStrategy); pi.visitFrame(Opcodes.F_NEW, 1, new Object[] { Opcodes.DOUBLE }, 0, new Object[] {}); // The locals in this frame are filled with TOP up to the probe variable expectedVisitor.visitFrame(Opcodes.F_NEW, 6, new Object[] { // Opcodes.DOUBLE, // Opcodes.TOP, // Opcodes.TOP, // Opcodes.TOP, // Opcodes.TOP, // safety slot "[Z", // probe array }, 0, new Object[] {}); } @Test public void visitFrame_should_not_insert_safety_slot_when_it_is_the_last_occupied_slot() { ProbeInserter pi = new ProbeInserter(0, "m", "()V", actualVisitor, arrayStrategy); pi.visitFrame(Opcodes.F_NEW, 1, new Object[] { // Opcodes.DOUBLE // }, 0, new Object[] {}); expectedVisitor.visitFrame(Opcodes.F_NEW, 2, new Object[] { // Opcodes.DOUBLE, // "[Z" // probe array }, 0, new Object[] {}); } @Test public void visitFrame_should_insert_TOP_after_probe_variable_when_safety_slot_occupied_but_not_the_last() { ProbeInserter pi = new ProbeInserter(0, "m", "()V", actualVisitor, arrayStrategy); pi.visitFrame(Opcodes.F_NEW, 2, new Object[] { // Opcodes.DOUBLE, // Opcodes.INTEGER // }, 0, new Object[] {}); expectedVisitor.visitFrame(Opcodes.F_NEW, 4, new Object[] { // Opcodes.DOUBLE, // "[Z", // probe array Opcodes.TOP, // Opcodes.INTEGER, // }, 0, new Object[] {}); } @Test(expected = IllegalArgumentException.class) public void visitFrame_must_only_support_resolved_frames() { ProbeInserter pi = new ProbeInserter(0, "m", "()V", actualVisitor, arrayStrategy); pi.visitFrame(Opcodes.F_SAME, 0, null, 0, null); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/instr/SafetySlotTest.java000066400000000000000000000104501451257705100313160ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.instr; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.runtime.IRuntime; import org.jacoco.core.runtime.RuntimeData; import org.jacoco.core.runtime.SystemPropertiesRuntime; import org.jacoco.core.test.TargetLoader; import org.jacoco.core.test.validation.JavaVersion; import org.junit.Test; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.Label; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; /** * This test verifies that instrumentation can handle case when the last local * variable of method parameters is overridden in the method body to store * a * value of type long or double which occupy two variables. * * @see ProbeInserterTest#visitFrame_should_not_insert_safety_slot_when_it_is_the_last_occupied_slot() * @see ProbeInserterTest#visitFrame_should_insert_TOP_after_probe_variable_when_safety_slot_occupied_but_not_the_last() */ public class SafetySlotTest { @Test public void jvm_should_verify_original_class_without_errors() throws Exception { final byte[] original = createClass(); new TargetLoader().add("Sample", original).newInstance(); } @Test public void jvm_should_verify_instrumented_class_without_errors() throws Exception { final IRuntime runtime = new SystemPropertiesRuntime(); runtime.startup(new RuntimeData()); final byte[] original = createClass(); final byte[] instrumented = new Instrumenter(runtime) .instrument(original, "Sample"); new TargetLoader().add("Sample", instrumented).newInstance(); } private static byte[] createClass() { final ClassWriter writer = new ClassWriter(0); writer.visit(bytecodeVersion(), Opcodes.ACC_PUBLIC, "Sample", null, "java/lang/Object", new String[0]); MethodVisitor mv = writer.visitMethod(Opcodes.ACC_PUBLIC, "", "()V", null, new String[0]); mv.visitCode(); mv.visitVarInsn(Opcodes.ALOAD, 0); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/Object", "", "()V", false); // Put a long value (2 slots) on position 0, overwriting 'this' mv.visitLdcInsn(Long.valueOf(42)); mv.visitVarInsn(Opcodes.LSTORE, 0); mv.visitInsn(Opcodes.ICONST_0); final Label label1 = new Label(); mv.visitJumpInsn(Opcodes.IFEQ, label1); mv.visitJumpInsn(Opcodes.GOTO, label1); mv.visitLabel(label1); mv.visitFrame(Opcodes.F_NEW, 1, new Object[] { Opcodes.LONG }, 0, new Object[] {}); mv.visitLdcInsn(Integer.valueOf(13)); mv.visitVarInsn(Opcodes.ISTORE, 2); mv.visitInsn(Opcodes.ICONST_0); final Label label2 = new Label(); mv.visitJumpInsn(Opcodes.IFEQ, label2); mv.visitJumpInsn(Opcodes.GOTO, label2); mv.visitLabel(label2); mv.visitFrame(Opcodes.F_NEW, 2, new Object[] { Opcodes.LONG, Opcodes.INTEGER }, 0, new Object[] {}); mv.visitInsn(Opcodes.RETURN); mv.visitMaxs(2, 3); mv.visitEnd(); writer.visitEnd(); return writer.toByteArray(); } /** * According to Java Virtual Machine Specification * §4.10.1: * *
*

* A class file whose version number is 50.0 or above (§4.1) must be * verified using the type checking rules given in this section. *

*

* If, and only if, a class file's version number equals 50.0, then if the * type checking fails, a Java Virtual Machine implementation may choose to * attempt to perform verification by type inference (§4.10.2). *

*
* * @return {@link Opcodes#V1_7} if supported by current JVM, * {@link Opcodes#V1_5} otherwise */ private static int bytecodeVersion() { return JavaVersion.current().isBefore("7") ? Opcodes.V1_5 : Opcodes.V1_7; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/instr/SignatureRemoverTest.java000066400000000000000000000066531451257705100325340ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.instr; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.InputStream; import java.util.jar.Manifest; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link SignatureRemover}. */ public class SignatureRemoverTest { private SignatureRemover remover; @Before public void setup() { remover = new SignatureRemover(); } @Test public void testRemoveNegative1() { assertFalse(remover.removeEntry("META-INF/ALIAS.MF")); } @Test public void testRemoveNegative2() { assertFalse(remover.removeEntry("META-INF/sub/ALIAS.SF")); } @Test public void testRemoveNegative3() { remover.setActive(false); assertFalse(remover.removeEntry("META-INF/SIG-ALIAS")); } @Test public void testRemovePositive1() { assertTrue(remover.removeEntry("META-INF/ALIAS.SF")); } @Test public void testRemovePositive2() { assertTrue(remover.removeEntry("META-INF/ALIAS.RSA")); } @Test public void testRemovePositive3() { assertTrue(remover.removeEntry("META-INF/ALIAS.DSA")); } @Test public void testRemovePositive4() { assertTrue(remover.removeEntry("META-INF/SIG-ALIAS")); } @Test public void testFilterNegative1() throws IOException { assertFalse(remover.filterEntry("MANIFEST.MF", null, null)); } @Test public void testFilterNegative2() throws IOException { remover.setActive(false); assertFalse(remover.filterEntry("META-INF/MANIFEST.MF", null, null)); } @Test public void testFilterPositive1() throws IOException { String original = "Manifest-Version: 1.0\r\n" + "Created-By: Apache Maven\r\n" // + "Bundle-SymbolicName: org.jacoco.core\r\n" // + "\r\n"// + "Name: org/jacoco/example/A.class\r\n" // + "SHA1-Digest: z1ly8OewPb9LOCpfNaIAhEgXZ5I=\r\n" // + "\r\n" // + "Name: org/jacoco/example/B.class\r\n" // + "SHA1-Digest: nfE4+Vmekj0pE5z0m0frpb10Gl0=\r\n" // + "OtherInfo: keep this\r\n" // + "\r\n" // + "Name: org/jacoco/example/C.class\r\n" // + "SHA1-Digest: xaNEXNWCrlTVcqPrXL0TwTcsvXU=\r\n"; InputStream in = new ByteArrayInputStream( original.getBytes("ISO-8859-1")); ByteArrayOutputStream out = new ByteArrayOutputStream(); assertTrue(remover.filterEntry("META-INF/MANIFEST.MF", in, out)); String expected = "Manifest-Version: 1.0\r\n" + "Created-By: Apache Maven\r\n" // + "Bundle-SymbolicName: org.jacoco.core\r\n" // + "\r\n"// + "Name: org/jacoco/example/B.class\r\n" // + "OtherInfo: keep this\r\n" // + "\r\n"; assertEquals(createManifest(expected.getBytes("ISO-8859-1")), createManifest(out.toByteArray())); } private static Manifest createManifest(final byte[] bytes) throws IOException { return new Manifest(new ByteArrayInputStream(bytes)); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/internal/instr/ZeroLineNumberTest.java000066400000000000000000000063121451257705100321230ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.instr; import static org.junit.Assert.assertEquals; import static org.junit.Assert.fail; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.internal.data.CRC64; import org.jacoco.core.runtime.IRuntime; import org.jacoco.core.runtime.RuntimeData; import org.jacoco.core.runtime.SystemPropertiesRuntime; import org.jacoco.core.test.TargetLoader; import org.junit.Test; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.Label; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; /** * @see org.jacoco.core.internal.flow.LabelFlowAnalyzer#visitLineNumber(int, * Label) * @see org.jacoco.core.internal.analysis.MethodAnalyzerTest#zero_line_number_should_create_1_probe() */ public class ZeroLineNumberTest { @Test public void zero_line_numbers_should_be_preserved_during_instrumentation_and_should_not_cause_insertion_of_additional_probes() throws Exception { final IRuntime runtime = new SystemPropertiesRuntime(); final RuntimeData data = new RuntimeData(); runtime.startup(data); final byte[] original = createClass(); final byte[] instrumented = new Instrumenter(runtime) .instrument(original, "Sample"); final Class cls = new TargetLoader().add("Sample", instrumented); try { cls.newInstance(); fail("Exception expected"); } catch (final Exception e) { assertEquals(0, e.getStackTrace()[1].getLineNumber()); } data.getExecutionData(CRC64.classId(original), "Sample", 2); } private static byte[] createClass() { final ClassWriter cv = new ClassWriter(ClassWriter.COMPUTE_MAXS); cv.visit(Opcodes.V1_5, Opcodes.ACC_PUBLIC, "Sample", null, "java/lang/Object", null); cv.visitSource("Sample.java", null); MethodVisitor mv = cv.visitMethod(Opcodes.ACC_PUBLIC, "", "()V", null, null); mv.visitCode(); final Label label1 = new Label(); mv.visitLabel(label1); mv.visitLineNumber(1, label1); mv.visitVarInsn(Opcodes.ALOAD, 0); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/Object", "", "()V", false); final Label label2 = new Label(); mv.visitLabel(label2); mv.visitLineNumber(0, label2); mv.visitMethodInsn(Opcodes.INVOKESTATIC, "Sample", "throw", "()V", false); mv.visitInsn(Opcodes.RETURN); mv.visitMaxs(0, 0); mv.visitEnd(); mv = cv.visitMethod(Opcodes.ACC_STATIC, "throw", "()V", null, null); mv.visitCode(); mv.visitTypeInsn(Opcodes.NEW, "java/lang/RuntimeException"); mv.visitInsn(Opcodes.DUP); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/RuntimeException", "", "()V", false); mv.visitInsn(Opcodes.ATHROW); mv.visitMaxs(0, 0); mv.visitEnd(); cv.visitEnd(); return cv.toByteArray(); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/runtime/000077500000000000000000000000001451257705100242265ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/runtime/AgentOptionsTest.java000066400000000000000000000335201451257705100303460ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.runtime; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import java.io.File; import java.util.Properties; import org.junit.BeforeClass; import org.junit.Test; /** * Unit tests for {@link AgentOptions}. */ public class AgentOptionsTest { private static File defaultAgentJarFile; @BeforeClass public static void beforeClass() { defaultAgentJarFile = new File("jacocoagent.jar"); } @Test public void testDefaults() { AgentOptions options = new AgentOptions(); assertEquals(AgentOptions.DEFAULT_DESTFILE, options.getDestfile()); assertTrue(options.getAppend()); assertEquals("*", options.getIncludes()); assertEquals("", options.getExcludes()); assertEquals("sun.reflect.DelegatingClassLoader", options.getExclClassloader()); assertFalse(options.getInclBootstrapClasses()); assertFalse(options.getInclNoLocationClasses()); assertNull(options.getSessionId()); assertTrue(options.getDumpOnExit()); assertEquals(AgentOptions.OutputMode.file, options.getOutput()); assertEquals(AgentOptions.DEFAULT_ADDRESS, options.getAddress()); assertEquals(AgentOptions.DEFAULT_PORT, options.getPort()); assertNull(options.getClassDumpDir()); assertFalse(options.getJmx()); assertEquals("", options.toString()); } @Test public void testEmptyOptions() { AgentOptions options = new AgentOptions(""); assertEquals("", options.toString()); } @Test public void testNullOptions() { AgentOptions options = new AgentOptions((String) null); assertEquals("", options.toString()); } @Test public void testPropertiesOptions() { Properties properties = new Properties(); properties.put("destfile", "/target/test/test.exec"); properties.put("append", "false"); properties.put("includes", "org.*:com.*"); properties.put("excludes", "*Test"); properties.put("exclclassloader", "org.jacoco.test.TestLoader"); properties.put("inclbootstrapclasses", "true"); properties.put("inclnolocationclasses", "true"); properties.put("sessionid", "testsession"); properties.put("dumponexit", "false"); properties.put("output", "tcpserver"); properties.put("address", "remotehost"); properties.put("port", "1234"); properties.put("classdumpdir", "target/dump"); properties.put("jmx", "true"); AgentOptions options = new AgentOptions(properties); assertEquals("/target/test/test.exec", options.getDestfile()); assertFalse(options.getAppend()); assertEquals("org.*:com.*", options.getIncludes()); assertEquals("*Test", options.getExcludes()); assertEquals("org.jacoco.test.TestLoader", options.getExclClassloader()); assertTrue(options.getInclBootstrapClasses()); assertTrue(options.getInclNoLocationClasses()); assertEquals("testsession", options.getSessionId()); assertFalse(options.getDumpOnExit()); assertEquals(AgentOptions.OutputMode.tcpserver, options.getOutput()); assertEquals("remotehost", options.getAddress()); assertEquals(1234, options.getPort()); assertEquals("target/dump", options.getClassDumpDir()); assertTrue(options.getJmx()); } @Test public void testEmptyPropertiesOptions() { AgentOptions options = new AgentOptions(new Properties()); assertEquals("", options.toString()); } @Test public void testGetDestile() { AgentOptions options = new AgentOptions("destfile=/var/test.exec"); assertEquals("/var/test.exec", options.getDestfile()); } @Test public void testSetDestile() { AgentOptions options = new AgentOptions(); options.setDestfile("/var/test.exec"); assertEquals("/var/test.exec", options.getDestfile()); assertEquals("destfile=/var/test.exec", options.toString()); } @Test public void testGetAppendTrue() { AgentOptions options = new AgentOptions("append=true"); assertTrue(options.getAppend()); } @Test public void testGetAppendFalse() { AgentOptions options = new AgentOptions("append=false"); assertFalse(options.getAppend()); } @Test public void testSetAppendTrue() { AgentOptions options = new AgentOptions(); options.setAppend(true); assertTrue(options.getAppend()); assertEquals("append=true", options.toString()); } @Test public void testSetAppendFalse() { AgentOptions options = new AgentOptions(); options.setAppend(false); assertFalse(options.getAppend()); assertEquals("append=false", options.toString()); } @Test public void testGetExclClassloader() { AgentOptions options = new AgentOptions( "exclclassloader=org.jacoco.test.TestLoader"); assertEquals("org.jacoco.test.TestLoader", options.getExclClassloader()); } @Test public void testSetExclClassloader() { AgentOptions options = new AgentOptions(); options.setExclClassloader("org.jacoco.test.TestLoader"); assertEquals("org.jacoco.test.TestLoader", options.getExclClassloader()); assertEquals("exclclassloader=org.jacoco.test.TestLoader", options.toString()); } @Test public void testGetIncludes() { AgentOptions options = new AgentOptions("includes=org.*:com.*"); assertEquals("org.*:com.*", options.getIncludes()); } @Test public void testSetIncludes() { AgentOptions options = new AgentOptions(); options.setIncludes("org.jacoco.*"); assertEquals("org.jacoco.*", options.getIncludes()); assertEquals("includes=org.jacoco.*", options.toString()); } @Test public void testGetExcludes() { AgentOptions options = new AgentOptions("excludes=*Test"); assertEquals("*Test", options.getExcludes()); } @Test public void testSetExcludes() { AgentOptions options = new AgentOptions(); options.setExcludes("org.jacoco.test.*"); assertEquals("org.jacoco.test.*", options.getExcludes()); assertEquals("excludes=org.jacoco.test.*", options.toString()); } @Test public void testGetInclBootstrapClassesTrue() { AgentOptions options = new AgentOptions("inclbootstrapclasses=true"); assertTrue(options.getInclBootstrapClasses()); } @Test public void testGetInclBootstrapClassesFalse() { AgentOptions options = new AgentOptions("inclbootstrapclasses=false"); assertFalse(options.getInclBootstrapClasses()); } @Test public void testSetInclBootstrapClassesTrue() { AgentOptions options = new AgentOptions(); options.setInclBootstrapClasses(true); assertTrue(options.getInclBootstrapClasses()); assertEquals("inclbootstrapclasses=true", options.toString()); } @Test public void testSetInclBootstrapClassesFalse() { AgentOptions options = new AgentOptions(); options.setInclBootstrapClasses(false); assertFalse(options.getInclBootstrapClasses()); assertEquals("inclbootstrapclasses=false", options.toString()); } @Test public void testGetInclNoLocationClassesTrue() { AgentOptions options = new AgentOptions("inclnolocationclasses=true"); assertTrue(options.getInclNoLocationClasses()); } @Test public void testGetInclNoLocationClassesFalse() { AgentOptions options = new AgentOptions("inclnolocationclasses=false"); assertFalse(options.getInclNoLocationClasses()); } @Test public void testSetInclNoLocationClassesTrue() { AgentOptions options = new AgentOptions(); options.setInclNoLocationClasses(true); assertTrue(options.getInclNoLocationClasses()); assertEquals("inclnolocationclasses=true", options.toString()); } @Test public void testSetInclNoLocationClassesFalse() { AgentOptions options = new AgentOptions(); options.setInclNoLocationClasses(false); assertFalse(options.getInclNoLocationClasses()); assertEquals("inclnolocationclasses=false", options.toString()); } @Test public void testGetSessionId() { AgentOptions options = new AgentOptions("sessionid=testsession"); assertEquals("testsession", options.getSessionId()); } @Test public void testSetSessionId() { AgentOptions options = new AgentOptions(); options.setSessionId("testsession"); assertEquals("testsession", options.getSessionId()); assertEquals("sessionid=testsession", options.toString()); } @Test public void testGetDumpOnExit() { AgentOptions options = new AgentOptions("dumponexit=false"); assertFalse(options.getDumpOnExit()); } @Test public void testSetDumpOnExit() { AgentOptions options = new AgentOptions(); options.setDumpOnExit(false); assertFalse(options.getDumpOnExit()); } @Test public void testGetOutput() { AgentOptions options = new AgentOptions("output=tcpserver"); assertEquals(AgentOptions.OutputMode.tcpserver, options.getOutput()); } @Test public void testSetOutput1() { AgentOptions options = new AgentOptions(); options.setOutput("tcpclient"); assertEquals(AgentOptions.OutputMode.tcpclient, options.getOutput()); } @Test public void testSetOutput2() { AgentOptions options = new AgentOptions(); options.setOutput(AgentOptions.OutputMode.tcpclient); assertEquals(AgentOptions.OutputMode.tcpclient, options.getOutput()); } @Test(expected = IllegalArgumentException.class) public void testInvalidOutput1() { new AgentOptions("output=foo"); } @Test(expected = IllegalArgumentException.class) public void testInvalidOutput2() { AgentOptions options = new AgentOptions(); options.setOutput("foo"); } @Test public void testGetPort() { AgentOptions options = new AgentOptions("port=1234"); assertEquals(1234, options.getPort()); } @Test public void testSetPort() { AgentOptions options = new AgentOptions(); options.setPort(1234); assertEquals(1234, options.getPort()); } @Test(expected = IllegalArgumentException.class) public void testParseInvalidPort() { new AgentOptions("port=xxx"); } @Test(expected = IllegalArgumentException.class) public void testSetNegativePort() { AgentOptions options = new AgentOptions(); options.setPort(-1234); } @Test public void testGetAddress() { AgentOptions options = new AgentOptions("address=remotehost"); assertEquals("remotehost", options.getAddress()); } @Test public void testSetAddress() { AgentOptions options = new AgentOptions(); options.setAddress("remotehost"); assertEquals("remotehost", options.getAddress()); } @Test public void testToString() { AgentOptions options = new AgentOptions(); options.setDestfile("test.exec"); options.setAppend(false); assertEquals("destfile=test.exec,append=false", options.toString()); } @Test(expected = IllegalArgumentException.class) public void testInvalidOptionFormat() { new AgentOptions("destfile"); } @Test(expected = IllegalArgumentException.class) public void testInvalidOptionKey() { new AgentOptions("destfile=test.exec,Some-thing_1=true"); } @Test(expected = IllegalArgumentException.class) public void testInvalidPortOptionValue() { new AgentOptions("port=-1234"); } @Test public void testGetClassDumpDir() { AgentOptions options = new AgentOptions("classdumpdir=target/dump"); assertEquals("target/dump", options.getClassDumpDir()); } @Test public void testSetClassDumpDir() { AgentOptions options = new AgentOptions(); options.setClassDumpDir("target/dump"); assertEquals("target/dump", options.getClassDumpDir()); assertEquals("classdumpdir=target/dump", options.toString()); } @Test public void testGetJmx() { AgentOptions options = new AgentOptions("jmx=true"); assertTrue(options.getJmx()); } @Test public void testSetJmx() { AgentOptions options = new AgentOptions(); options.setJmx(true); assertTrue(options.getJmx()); } @Test public void testGetVMArgumentWithNoOptions() { AgentOptions options = new AgentOptions(); String vmArgument = options.getVMArgument(defaultAgentJarFile); assertEquals( String.format("-javaagent:%s=", defaultAgentJarFile.toString()), vmArgument); } @Test public void testGetVMArgumentWithOneOption() { AgentOptions options = new AgentOptions(); options.setAppend(true); String vmArgument = options.getVMArgument(defaultAgentJarFile); assertEquals(String.format("-javaagent:%s=append=true", defaultAgentJarFile.toString()), vmArgument); } @Test public void testGetVMArgumentWithOptions() { AgentOptions options = new AgentOptions(); options.setAppend(true); options.setDestfile("some test.exec"); String vmArgument = options.getVMArgument(defaultAgentJarFile); assertEquals(String.format( "-javaagent:%s=destfile=some test.exec,append=true", defaultAgentJarFile.toString()), vmArgument); } @Test public void testGetQuotedVMArgument() { AgentOptions options = new AgentOptions(); options.setSessionId("my session"); String vmArgument = options.getQuotedVMArgument(defaultAgentJarFile); assertEquals(String.format("\"-javaagent:%s=sessionid=my session\"", defaultAgentJarFile.toString()), vmArgument); } @Test public void testPrependVMArguments() { AgentOptions options = new AgentOptions(); String vmArgument = options.prependVMArguments("a b c", defaultAgentJarFile); assertEquals(String.format("-javaagent:%s= a b c", defaultAgentJarFile.toString()), vmArgument); } @Test public void testPrependVMArgumentsReplace() { AgentOptions options = new AgentOptions(); String vmArgument = options.prependVMArguments( String.format("a b -javaagent:%s=append=false c", defaultAgentJarFile), defaultAgentJarFile); assertEquals(String.format("-javaagent:%s= a b c", defaultAgentJarFile.toString()), vmArgument); } @Test public void testOptionValueWithSpecialCharacters() { AgentOptions options = new AgentOptions( "destfile=build/jacoco/foo, bar-1_0.exec"); assertEquals("build/jacoco/foo, bar-1_0.exec", options.getDestfile()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/runtime/CommandLineSupportTest.java000066400000000000000000000055471451257705100315270ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.runtime; import static org.junit.Assert.assertEquals; import java.util.Arrays; import org.junit.Test; /** * Unit tests for {@link CommandLineSupport}. */ public class CommandLineSupportTest { @Test public void testQuote1() { assertEquals("aBc", CommandLineSupport.quote("aBc")); } @Test public void testQuote2() { assertEquals("\"a c\"", CommandLineSupport.quote("a c")); } @Test public void testQuote3() { assertEquals("\"a\\\"c\"", CommandLineSupport.quote("a\"c")); } @Test public void testQuote4() { assertEquals("\" xy \"", CommandLineSupport.quote(" xy ")); } @Test public void testQuote5() { assertEquals("a\\\\b", CommandLineSupport.quote("a\\b")); } @Test public void testQuoteList1() { assertEquals("", CommandLineSupport.quote(Arrays. asList())); } @Test public void testQuoteList2() { assertEquals("a", CommandLineSupport.quote(Arrays.asList("a"))); } @Test public void testQuoteList3() { assertEquals("a b c", CommandLineSupport.quote(Arrays.asList("a", "b", "c"))); } @Test public void testQuoteList4() { assertEquals("a \"b b\" c", CommandLineSupport.quote(Arrays.asList("a", "b b", "c"))); } @Test public void testSplit1() { assertEquals(Arrays.asList(), CommandLineSupport.split(null)); } @Test public void testSplit2() { assertEquals(Arrays.asList(), CommandLineSupport.split("")); } @Test public void testSplit3() { assertEquals(Arrays.asList("abc"), CommandLineSupport.split("abc")); } @Test public void testSplit4() { assertEquals(Arrays.asList("aa", "bbbb", "cccccc"), CommandLineSupport.split(" aa bbbb cccccc ")); } @Test public void testSplit5() { assertEquals(Arrays.asList("a a", "b b "), CommandLineSupport.split("\"a a\" \"b b \" ")); } @Test public void testSplit6() { assertEquals(Arrays.asList("a\"c"), CommandLineSupport.split("a\\\"c")); } @Test public void testSplit7() { assertEquals(Arrays.asList("a\\c"), CommandLineSupport.split("a\\c")); } @Test public void testSplit8() { assertEquals(Arrays.asList("a\\"), CommandLineSupport.split("a\\")); } @Test public void testSplit9() { assertEquals(Arrays.asList("a\\", "b"), CommandLineSupport.split("a\\ b")); } @Test public void testSplit10() { assertEquals(Arrays.asList("a\\b"), CommandLineSupport.split("a\\\\b")); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/runtime/InjectedClassRuntimeTest.java000066400000000000000000000034021451257705100320070ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.runtime; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.lang.reflect.InvocationTargetException; import org.junit.AssumptionViolatedException; import org.junit.BeforeClass; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TestName; /** * Unit test for {@link InjectedClassRuntime}. */ public class InjectedClassRuntimeTest extends RuntimeTestBase { @Rule public TestName testName = new TestName(); @BeforeClass public static void requires_at_least_Java_9() { try { Class.forName("java.lang.Module"); } catch (final ClassNotFoundException e) { throw new AssumptionViolatedException( "this test requires at least Java 9"); } } @Override public IRuntime createRuntime() { return new InjectedClassRuntime(InjectedClassRuntimeTest.class, testName.getMethodName()); } @Test public void startup_should_not_create_duplicate_class_definition() throws Exception { try { createRuntime().startup(null); fail("exception expected"); } catch (final InvocationTargetException e) { assertTrue(e.getCause() instanceof LinkageError); assertTrue(e.getCause().getMessage() .contains("duplicate class definition")); } } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/runtime/LoggerRuntimeTest.java000066400000000000000000000013571451257705100305220ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.runtime; /** * Unit tests for {@link LoggerRuntime}. */ public class LoggerRuntimeTest extends RuntimeTestBase { @Override IRuntime createRuntime() { return new LoggerRuntime(); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/runtime/ModifiedSystemClassRuntimeTest.java000066400000000000000000000100751451257705100332130ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.runtime; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.lang.instrument.ClassFileTransformer; import java.lang.instrument.Instrumentation; import java.lang.reflect.Field; import java.lang.reflect.InvocationHandler; import java.lang.reflect.Method; import java.lang.reflect.Modifier; import java.lang.reflect.Proxy; import org.jacoco.core.test.TargetLoader; import org.junit.Test; /** * Unit tests for {@link ModifiedSystemClassRuntime}. */ public class ModifiedSystemClassRuntimeTest extends RuntimeTestBase { @Override IRuntime createRuntime() { return new ModifiedSystemClassRuntime( ModifiedSystemClassRuntimeTest.class, "accessField"); } @Test(expected = RuntimeException.class) public void testCreateForNegative() throws Exception { Instrumentation inst = newInstrumentationMock(); ModifiedSystemClassRuntime.createFor(inst, TARGET_CLASS_NAME); } /** This static member emulate the instrumented system class. */ public static Object accessField; private static final String TARGET_CLASS_NAME = "org/jacoco/core/runtime/ModifiedSystemClassRuntimeTest"; /** * Note that we use Proxy here to mock {@link Instrumentation}, because JDK * 9 adds new method "addModule", whose parameter depends on class * "java.lang.reflect.Module" introduced in JDK 9. */ private Instrumentation newInstrumentationMock() { return (Instrumentation) Proxy.newProxyInstance( getClass().getClassLoader(), new Class[] { Instrumentation.class }, new MyInvocationHandler()); } private static class MyInvocationHandler implements InvocationHandler { boolean added = false; boolean removed = false; /** * {@link Instrumentation#addTransformer(ClassFileTransformer)} */ void addTransformer(ClassFileTransformer transformer) { assertFalse(added); added = true; try { // Our class should get instrumented: final byte[] data = TargetLoader.getClassDataAsBytes( ModifiedSystemClassRuntimeTest.class); verifyInstrumentedClass(TARGET_CLASS_NAME, transformer.transform((ClassLoader) null, TARGET_CLASS_NAME, null, null, data)); // Other classes will not be instrumented: assertNull(transformer.transform(getClass().getClassLoader(), "some/other/Class", null, null, new byte[0])); } catch (Exception e) { throw new RuntimeException(e); } } /** * {@link Instrumentation#removeTransformer(ClassFileTransformer)} */ Boolean removeTransformer() { assertTrue(added); assertFalse(removed); removed = true; return Boolean.TRUE; } public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { if (args.length == 1) { if ("removeTransformer".equals(method.getName())) { return removeTransformer(); } else if ("addTransformer".equals(method.getName())) { addTransformer((ClassFileTransformer) args[0]); return null; } } fail(); return null; } } private static void verifyInstrumentedClass(String name, byte[] source) throws Exception { name = name.replace('/', '.'); final Class targetClass = new TargetLoader().add(name, source); // Check added field: final Field f = targetClass.getField("$jacocoAccess"); assertTrue(Modifier.isPublic(f.getModifiers())); assertTrue(Modifier.isStatic(f.getModifiers())); assertTrue(Modifier.isTransient(f.getModifiers())); assertEquals(Object.class, f.getType()); } } OfflineInstrumentationAccessGeneratorTest.java000066400000000000000000000111471451257705100353550ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/runtime/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.runtime; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertSame; import org.jacoco.core.JaCoCo; import org.jacoco.core.instr.MethodRecorder; import org.jacoco.core.internal.instr.InstrSupport; import org.jacoco.core.test.TargetLoader; import org.junit.Before; import org.junit.BeforeClass; import org.junit.Test; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.Opcodes; import org.objectweb.asm.Type; import org.objectweb.asm.commons.GeneratorAdapter; import org.objectweb.asm.commons.Method; /** * Unit tests for {@link OfflineInstrumentationAccessGenerator}. */ public class OfflineInstrumentationAccessGeneratorTest { private IExecutionDataAccessorGenerator generator; private static boolean[] probes; // runtime stub public static boolean[] getProbes(final long classid, final String classname, final int probecount) { return probes; } @BeforeClass public static void setupClass() { probes = new boolean[3]; } @Before public void setup() { String name = getClass().getName().replace('.', '/'); generator = new OfflineInstrumentationAccessGenerator(name); } @Test public void testRuntimeAccess() throws Exception { ITarget target = generateAndInstantiateClass(123); assertSame(probes, target.get()); } @Test public void testRuntimeClassName() throws Exception { generator = new OfflineInstrumentationAccessGenerator(); MethodRecorder actual = new MethodRecorder(); generator.generateDataAccessor(987654321, "foo/Bar", 17, actual.getVisitor()); MethodRecorder expected = new MethodRecorder(); expected.getVisitor().visitLdcInsn(Long.valueOf(987654321)); expected.getVisitor().visitLdcInsn("foo/Bar"); expected.getVisitor().visitIntInsn(Opcodes.BIPUSH, 17); String rtname = JaCoCo.RUNTIMEPACKAGE.replace('.', '/') + "/Offline"; expected.getVisitor().visitMethodInsn(Opcodes.INVOKESTATIC, rtname, "getProbes", "(JLjava/lang/String;I)[Z", false); assertEquals(expected, actual); } /** * Creates a new class with the given id, loads this class and instantiates * it. The constructor of the generated class will request the probe array * from the access generator under test. */ private ITarget generateAndInstantiateClass(int classid) throws InstantiationException, IllegalAccessException { final String className = "org/jacoco/test/targets/RuntimeTestTarget_" + classid; Type classType = Type.getObjectType(className); final ClassWriter writer = new ClassWriter(0); writer.visit(Opcodes.V1_5, Opcodes.ACC_PUBLIC, className, null, "java/lang/Object", new String[] { Type.getInternalName(ITarget.class) }); writer.visitField(InstrSupport.DATAFIELD_ACC, InstrSupport.DATAFIELD_NAME, InstrSupport.DATAFIELD_DESC, null, null); // Constructor GeneratorAdapter gen = new GeneratorAdapter( writer.visitMethod(Opcodes.ACC_PUBLIC, "", "()V", null, new String[0]), Opcodes.ACC_PUBLIC, "", "()V"); gen.visitCode(); gen.loadThis(); gen.invokeConstructor(Type.getType(Object.class), new Method("", "()V")); gen.loadThis(); final int size = generator.generateDataAccessor(classid, className, 2, gen); gen.putStatic(classType, InstrSupport.DATAFIELD_NAME, Type.getObjectType(InstrSupport.DATAFIELD_DESC)); gen.returnValue(); gen.visitMaxs(size + 1, 0); gen.visitEnd(); // get() gen = new GeneratorAdapter(writer.visitMethod(Opcodes.ACC_PUBLIC, "get", "()[Z", null, new String[0]), Opcodes.ACC_PUBLIC, "get", "()[Z"); gen.visitCode(); gen.getStatic(classType, InstrSupport.DATAFIELD_NAME, Type.getObjectType(InstrSupport.DATAFIELD_DESC)); gen.returnValue(); gen.visitMaxs(1, 0); gen.visitEnd(); writer.visitEnd(); final TargetLoader loader = new TargetLoader(); return (ITarget) loader .add(className.replace('/', '.'), writer.toByteArray()) .newInstance(); } /** * With this interface access read coverage data of the generated class. */ public interface ITarget { /** * Returns a reference to the probe array. * * @return the probe array */ boolean[] get(); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/runtime/RemoteControlReaderWriterTest.java000066400000000000000000000056771451257705100330640ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.runtime; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import java.io.ByteArrayInputStream; import java.io.IOException; import java.io.OutputStream; import org.jacoco.core.data.ExecutionDataReader; import org.jacoco.core.data.ExecutionDataReaderWriterTest; import org.jacoco.core.data.ExecutionDataWriter; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link ExecutionDataReader} and {@link ExecutionDataWriter}. * The tests don't care about the written binary format, they just verify * symmetry. */ public class RemoteControlReaderWriterTest extends ExecutionDataReaderWriterTest { private RemoteControlWriter writer; @Before @Override public void setup() throws IOException { super.setup(); writer = createWriter(buffer); } @Test(expected = IOException.class) public void testNoRemoteCommandVisitor() throws IOException { writer.visitDumpCommand(false, false); final RemoteControlReader reader = createReader(); reader.read(); } @Test public void testVisitDump1() throws IOException { testVisitDump(false, false); } @Test public void testVisitDump2() throws IOException { testVisitDump(false, true); } @Test public void testVisitDump3() throws IOException { testVisitDump(true, false); } @Test public void testVisitDump4() throws IOException { testVisitDump(true, true); } private void testVisitDump(boolean doDump, boolean doReset) throws IOException { writer.visitDumpCommand(doDump, doReset); final RemoteControlReader reader = createReader(); final StringBuilder calls = new StringBuilder(); reader.setRemoteCommandVisitor(new IRemoteCommandVisitor() { public void visitDumpCommand(boolean dump, boolean reset) { calls.append("cmd(" + dump + "," + reset + ")"); } }); assertFalse(reader.read()); assertEquals("cmd(" + doDump + "," + doReset + ")", calls.toString()); } @Test public void testSendCmdOk() throws IOException { writer.sendCmdOk(); final RemoteControlReader reader = createReader(); assertTrue(reader.read()); } @Override protected RemoteControlReader createReader() throws IOException { return new RemoteControlReader( new ByteArrayInputStream(buffer.toByteArray())); } @Override protected RemoteControlWriter createWriter(OutputStream out) throws IOException { return new RemoteControlWriter(out); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/runtime/RuntimeDataTest.java000066400000000000000000000132361451257705100301530ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.runtime; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertSame; import static org.junit.Assert.assertTrue; import java.util.concurrent.Callable; import org.jacoco.core.test.TargetLoader; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; import org.objectweb.asm.Type; /** * Unit tests for {@link RuntimeData}. * */ public class RuntimeDataTest { private RuntimeData data; private TestStorage storage; @Before public void setup() { data = new RuntimeData(); storage = new TestStorage(); } @Test public void testGetSetSessionId() { assertNotNull(data.getSessionId()); data.setSessionId("test-id"); assertEquals("test-id", data.getSessionId()); } @Test public void testGetProbes() { Object[] args = new Object[] { Long.valueOf(123), "Foo", Integer.valueOf(3) }; data.equals(args); assertEquals(3, ((boolean[]) args[0]).length); data.collect(storage, storage, false); boolean[] data = (boolean[]) args[0]; assertEquals(3, data.length, 0.0); assertFalse(data[0]); assertFalse(data[1]); assertFalse(data[2]); assertSame(storage.getData(123).getProbes(), data); assertEquals("Foo", storage.getData(123).getName()); } @Test public void testCollectEmpty() { data.collect(storage, storage, false); storage.assertSize(0); } @Test public void testCollectWithReset() { data.setSessionId("testsession"); boolean[] probes = data.getExecutionData(Long.valueOf(123), "Foo", 1) .getProbes(); probes[0] = true; data.collect(storage, storage, true); assertFalse(probes[0]); assertEquals("testsession", storage.getSessionInfo().getId()); } @Test public void testCollectWithoutReset() { data.setSessionId("testsession"); boolean[] probes = data.getExecutionData(Long.valueOf(123), "Foo", 1) .getProbes(); probes[0] = true; data.collect(storage, storage, false); assertTrue(probes[0]); assertEquals("testsession", storage.getSessionInfo().getId()); } @Test public void testEquals() { assertTrue(data.equals(data)); } @Test public void testHashCode() { assertEquals(System.identityHashCode(data), data.hashCode()); } @Test public void testGenerateArgumentArray() throws Exception { final ClassWriter writer = new ClassWriter(0); writer.visit(Opcodes.V1_5, Opcodes.ACC_PUBLIC, "Sample", null, "java/lang/Object", new String[] { Type.getInternalName(Callable.class) }); // Constructor MethodVisitor mv = writer.visitMethod(Opcodes.ACC_PUBLIC, "", "()V", null, new String[0]); mv.visitCode(); mv.visitVarInsn(Opcodes.ALOAD, 0); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/Object", "", "()V", false); mv.visitInsn(Opcodes.RETURN); mv.visitMaxs(1, 1); mv.visitEnd(); // call() mv = writer.visitMethod(Opcodes.ACC_PUBLIC, "call", "()Ljava/lang/Object;", null, new String[0]); mv.visitCode(); RuntimeData.generateArgumentArray(1000, "Sample", 15, mv); mv.visitInsn(Opcodes.ARETURN); mv.visitMaxs(5, 1); mv.visitEnd(); writer.visitEnd(); final TargetLoader loader = new TargetLoader(); Callable callable = (Callable) loader .add("Sample", writer.toByteArray()).newInstance(); final Object[] args = (Object[]) callable.call(); assertEquals(3, args.length, 0.0); assertEquals(Long.valueOf(1000), args[0]); assertEquals("Sample", args[1]); assertEquals(Integer.valueOf(15), args[2]); } @Test public void testGenerateAccessCall() throws Exception { final boolean[] probes = data .getExecutionData(Long.valueOf(1234), "Sample", 5).getProbes(); final ClassWriter writer = new ClassWriter(0); writer.visit(Opcodes.V1_5, Opcodes.ACC_PUBLIC, "Sample", null, "java/lang/Object", new String[] { Type.getInternalName(Callable.class) }); // Constructor MethodVisitor mv = writer.visitMethod(Opcodes.ACC_PUBLIC, "", "(Ljava/lang/Object;)V", null, new String[0]); mv.visitCode(); mv.visitVarInsn(Opcodes.ALOAD, 0); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, "java/lang/Object", "", "()V", false); mv.visitVarInsn(Opcodes.ALOAD, 0); mv.visitVarInsn(Opcodes.ALOAD, 1); mv.visitFieldInsn(Opcodes.PUTFIELD, "Sample", "access", "Ljava/lang/Object;"); mv.visitInsn(Opcodes.RETURN); mv.visitMaxs(2, 2); mv.visitEnd(); // call() mv = writer.visitMethod(Opcodes.ACC_PUBLIC, "call", "()Ljava/lang/Object;", null, new String[0]); mv.visitCode(); mv.visitVarInsn(Opcodes.ALOAD, 0); mv.visitFieldInsn(Opcodes.GETFIELD, "Sample", "access", "Ljava/lang/Object;"); RuntimeData.generateAccessCall(1234, "Sample", 5, mv); mv.visitInsn(Opcodes.ARETURN); mv.visitMaxs(6, 1); mv.visitEnd(); writer.visitField(Opcodes.ACC_PRIVATE, "access", "Ljava/lang/Object;", null, null); writer.visitEnd(); final TargetLoader loader = new TargetLoader(); Callable callable = (Callable) loader .add("Sample", writer.toByteArray()) .getConstructor(Object.class).newInstance(data); assertSame(probes, callable.call()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/runtime/RuntimeTestBase.java000066400000000000000000000134751451257705100301610ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.runtime; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import org.jacoco.core.internal.instr.InstrSupport; import org.jacoco.core.test.TargetLoader; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.Opcodes; import org.objectweb.asm.Type; import org.objectweb.asm.commons.GeneratorAdapter; import org.objectweb.asm.commons.Method; /** * Abstract test base for {@link IRuntime} implementations. */ public abstract class RuntimeTestBase { private RuntimeData data; private IRuntime runtime; private TestStorage storage; abstract IRuntime createRuntime(); @Before public void setup() throws Exception { data = new RuntimeData(); runtime = createRuntime(); runtime.startup(data); storage = new TestStorage(); } @After public void shutdown() { runtime.shutdown(); } @Test public void testDataAccessor() throws InstantiationException, IllegalAccessException { ITarget t = generateAndInstantiateClass(1234); data.collect(storage, storage, false); storage.assertData(1234, t.get()); } @Test public void testNoLocalVariablesInDataAccessor() throws InstantiationException, IllegalAccessException { runtime.generateDataAccessor(1001, "Target", 5, new MethodVisitor(InstrSupport.ASM_API_VERSION) { @Override public void visitVarInsn(int opcode, int var) { fail("No usage of local variables allowed."); } }); } @Test public void testExecutionRecording() throws InstantiationException, IllegalAccessException { generateAndInstantiateClass(1001).a(); data.collect(storage, storage, false); storage.assertSize(1); final boolean[] data = storage.getData(1001).getProbes(); assertTrue(data[0]); assertFalse(data[1]); } @Test public void testLoadSameClassTwice() throws InstantiationException, IllegalAccessException { generateAndInstantiateClass(1001).a(); generateAndInstantiateClass(1001).b(); data.collect(storage, storage, false); storage.assertSize(1); final boolean[] data = storage.getData(1001).getProbes(); assertTrue(data[0]); assertTrue(data[1]); } /** * Creates a new class with the given id, loads this class and instantiates * it. The constructor of the generated class will request the probe array * from the runtime under test. */ private ITarget generateAndInstantiateClass(int classid) throws InstantiationException, IllegalAccessException { final String className = "org/jacoco/test/targets/RuntimeTestTarget_" + classid; Type classType = Type.getObjectType(className); final ClassWriter writer = new ClassWriter(0); writer.visit(Opcodes.V1_5, Opcodes.ACC_PUBLIC, className, null, "java/lang/Object", new String[] { Type.getInternalName(ITarget.class) }); writer.visitField(InstrSupport.DATAFIELD_ACC, InstrSupport.DATAFIELD_NAME, InstrSupport.DATAFIELD_DESC, null, null); // Constructor GeneratorAdapter gen = new GeneratorAdapter( writer.visitMethod(Opcodes.ACC_PUBLIC, "", "()V", null, new String[0]), Opcodes.ACC_PUBLIC, "", "()V"); gen.visitCode(); gen.loadThis(); gen.invokeConstructor(Type.getType(Object.class), new Method("", "()V")); gen.loadThis(); final int size = runtime.generateDataAccessor(classid, className, 2, gen); gen.putStatic(classType, InstrSupport.DATAFIELD_NAME, Type.getObjectType(InstrSupport.DATAFIELD_DESC)); gen.returnValue(); gen.visitMaxs(size + 1, 0); gen.visitEnd(); // get() gen = new GeneratorAdapter(writer.visitMethod(Opcodes.ACC_PUBLIC, "get", "()[Z", null, new String[0]), Opcodes.ACC_PUBLIC, "get", "()[Z"); gen.visitCode(); gen.getStatic(classType, InstrSupport.DATAFIELD_NAME, Type.getObjectType(InstrSupport.DATAFIELD_DESC)); gen.returnValue(); gen.visitMaxs(1, 0); gen.visitEnd(); // a() gen = new GeneratorAdapter(writer.visitMethod(Opcodes.ACC_PUBLIC, "a", "()V", null, new String[0]), Opcodes.ACC_PUBLIC, "a", "()V"); gen.visitCode(); gen.getStatic(classType, InstrSupport.DATAFIELD_NAME, Type.getObjectType(InstrSupport.DATAFIELD_DESC)); gen.push(0); gen.push(1); gen.arrayStore(Type.BOOLEAN_TYPE); gen.returnValue(); gen.visitMaxs(3, 0); gen.visitEnd(); // b() gen = new GeneratorAdapter(writer.visitMethod(Opcodes.ACC_PUBLIC, "b", "()V", null, new String[0]), Opcodes.ACC_PUBLIC, "b", "()V"); gen.visitCode(); gen.getStatic(classType, InstrSupport.DATAFIELD_NAME, Type.getObjectType(InstrSupport.DATAFIELD_DESC)); gen.push(1); gen.push(1); gen.arrayStore(Type.BOOLEAN_TYPE); gen.returnValue(); gen.visitMaxs(3, 0); gen.visitEnd(); writer.visitEnd(); final TargetLoader loader = new TargetLoader(); return (ITarget) loader .add(className.replace('/', '.'), writer.toByteArray()) .newInstance(); } /** * With this interface we modify and read coverage data of the generated * class. */ public interface ITarget { /** * Returns a reference to the probe array. * * @return the probe array */ boolean[] get(); /** * The implementation will mark probe 0 as executed */ void a(); /** * The implementation will mark probe 1 as executed */ void b(); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/runtime/SystemPropertiesRuntimeTest.java000066400000000000000000000014151451257705100326370ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.runtime; /** * Unit tests for {@link SystemPropertiesRuntime}. */ public class SystemPropertiesRuntimeTest extends RuntimeTestBase { @Override IRuntime createRuntime() { return new SystemPropertiesRuntime(); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/runtime/TestStorage.java000066400000000000000000000032131451257705100273340ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.runtime; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertSame; import java.util.HashMap; import java.util.Map; import org.jacoco.core.data.ExecutionData; import org.jacoco.core.data.IExecutionDataVisitor; import org.jacoco.core.data.ISessionInfoVisitor; import org.jacoco.core.data.SessionInfo; class TestStorage implements IExecutionDataVisitor, ISessionInfoVisitor { private final Map data = new HashMap(); private SessionInfo info; public void assertSize(int size) { assertEquals(size, data.size(), 0.0); } public ExecutionData getData(long classId) { return data.get(Long.valueOf(classId)); } public SessionInfo getSessionInfo() { return info; } public void assertData(long classId, boolean[] expected) { assertSame(expected, getData(classId).getProbes()); } // === ICoverageDataVisitor === public void visitClassExecution(final ExecutionData ed) { data.put(Long.valueOf(ed.getId()), ed); } // === ISessionInfoVisitor === public void visitSessionInfo(SessionInfo info) { this.info = info; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/runtime/WildcardMatcherTest.java000066400000000000000000000054131451257705100307710ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.runtime; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import org.junit.Test; public class WildcardMatcherTest { @Test public void empty_expression_should_match_any_string() { assertTrue(new WildcardMatcher("").matches("")); assertFalse(new WildcardMatcher("").matches("abc")); } @Test public void expressions_without_wildcards_should_match_exactly() { assertTrue(new WildcardMatcher("abc/def.txt").matches("abc/def.txt")); assertFalse(new WildcardMatcher("abc/def.txt").matches("/abc/def.txt")); } @Test public void should_match_case_sensitive() { assertFalse(new WildcardMatcher("abcdef").matches("abcDef")); assertFalse(new WildcardMatcher("ABCDEF").matches("AbCDEF")); } @Test public void should_not_use_regex_characters() { assertFalse(new WildcardMatcher("rst.xyz").matches("rstAxyz")); assertTrue(new WildcardMatcher("(x)+").matches("(x)+")); } @Test public void asterix_should_match_any_number_of_any_character() { assertTrue(new WildcardMatcher("*").matches("")); assertTrue(new WildcardMatcher("*").matches("java/lang/Object")); assertTrue(new WildcardMatcher("*Test").matches("jacoco/MatcherTest")); assertTrue(new WildcardMatcher("Matcher*").matches("Matcher")); assertTrue(new WildcardMatcher("Matcher*").matches("MatcherTest")); assertTrue(new WildcardMatcher("a*b*a").matches("a-b-b-a")); assertFalse(new WildcardMatcher("a*b*a").matches("alaska")); } @Test public void questionmark_should_match_any_single_character() { assertTrue(new WildcardMatcher("Hello?orld").matches("HelloWorld")); assertFalse(new WildcardMatcher("Hello?orld").matches("Helloorld")); assertFalse(new WildcardMatcher("Hello?orld").matches("HelloWWWorld")); } @Test public void should_match_any_expression_when_multiple_expressions_are_given() { assertTrue(new WildcardMatcher("Hello:World").matches("World")); assertTrue(new WildcardMatcher("*Test:*Foo").matches("UnitTest")); assertFalse(new WildcardMatcher("foo:bar").matches("foo:bar")); } @Test public void should_match_dollar_sign() { assertTrue(new WildcardMatcher("*$*").matches("java/util/Map$Entry")); assertTrue(new WildcardMatcher("*$$$*") .matches("org/example/Enity$$$generated123")); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/000077500000000000000000000000001451257705100235225ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/InstrumentingLoader.java000066400000000000000000000051241451257705100303640ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test; import java.io.IOException; import org.jacoco.core.data.ExecutionDataStore; import org.jacoco.core.data.SessionInfoStore; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.runtime.IRuntime; import org.jacoco.core.runtime.RuntimeData; import org.jacoco.core.runtime.SystemPropertiesRuntime; /** * Class loader which loads classes from another class loader and instruments * them. */ public final class InstrumentingLoader extends ClassLoader { private final IRuntime runtime; private final String scope; private final ClassLoader delegate; private final RuntimeData data; private final Instrumenter instrumenter; public InstrumentingLoader(IRuntime runtime, String scope, ClassLoader delegate) throws Exception { this.runtime = runtime; this.scope = scope; this.delegate = delegate; this.data = new RuntimeData(); runtime.startup(data); this.instrumenter = new Instrumenter(runtime); } public InstrumentingLoader(Class target) throws Exception { this(new SystemPropertiesRuntime(), target.getPackage().getName(), target.getClassLoader()); } @Override protected synchronized Class loadClass(String name, boolean resolve) throws ClassNotFoundException { if (name.startsWith(scope)) { Class c = findLoadedClass(name); if (c != null) { return c; } final byte[] bytes; try { bytes = TargetLoader.getClassDataAsBytes(delegate, name); } catch (IOException e) { throw new ClassNotFoundException("Unable to load", e); } final byte[] instrumented; try { instrumented = instrumenter.instrument(bytes, name); } catch (IOException e) { throw new ClassNotFoundException("Unable to instrument", e); } c = defineClass(name, instrumented, 0, instrumented.length); if (resolve) { resolveClass(c); } return c; } return super.loadClass(name, resolve); } public ExecutionDataStore collect() { final ExecutionDataStore store = new ExecutionDataStore(); data.collect(store, new SessionInfoStore(), false); runtime.shutdown(); return store; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/InstrumentingLoaderTest.java000066400000000000000000000021061451257705100312210ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test; import org.junit.Test; import static org.junit.Assert.assertSame; /** * Unit test for {@link InstrumentingLoader}. */ public class InstrumentingLoaderTest { @Test public void should_use_findLoadedClass() throws Exception { final InstrumentingLoader loader = new InstrumentingLoader( InstrumentingLoaderTest.class); final Class c1 = loader .loadClass(InstrumentingLoaderTest.class.getName()); final Class c2 = loader .loadClass(InstrumentingLoaderTest.class.getName()); assertSame(c1, c2); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/TargetLoader.java000066400000000000000000000051131451257705100267420ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.InputStream; import java.util.HashMap; import java.util.Map; /** * Loads given classes from a byte arrays. */ public class TargetLoader extends ClassLoader { private final Map classes; public TargetLoader() { super(TargetLoader.class.getClassLoader()); this.classes = new HashMap(); } public Class add(final String name, final byte[] bytes) { this.classes.put(name, bytes); return load(name); } public Class add(final Class name, final byte[] bytes) { return add(name.getName(), bytes); } private Class load(final String sourcename) { try { return loadClass(sourcename); } catch (ClassNotFoundException e) { // must not happen throw new RuntimeException(e); } } public static InputStream getClassData(Class clazz) { return getClassData(clazz.getClassLoader(), clazz.getName()); } public static InputStream getClassData(ClassLoader loader, String name) { final String resource = name.replace('.', '/') + ".class"; return loader.getResourceAsStream(resource); } public static byte[] getClassDataAsBytes(ClassLoader loader, String name) throws IOException { return readBytes(getClassData(loader, name)); } public static byte[] getClassDataAsBytes(Class clazz) throws IOException { return readBytes(getClassData(clazz)); } private static byte[] readBytes(InputStream in) throws IOException { ByteArrayOutputStream out = new ByteArrayOutputStream(); byte[] buffer = new byte[0x100]; int len; while ((len = in.read(buffer)) != -1) { out.write(buffer, 0, len); } in.close(); return out.toByteArray(); } @Override protected synchronized Class loadClass(String name, boolean resolve) throws ClassNotFoundException { final byte[] bytes = classes.get(name); if (bytes != null) { Class c = defineClass(name, bytes, 0, bytes.length); if (resolve) { resolveClass(c); } return c; } return super.loadClass(name, resolve); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/000077500000000000000000000000001451257705100244565ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/AnalysisTimeScenario.java000066400000000000000000000034511451257705100314120ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.perf; import java.util.concurrent.Callable; import org.jacoco.core.analysis.Analyzer; import org.jacoco.core.analysis.IClassCoverage; import org.jacoco.core.analysis.ICoverageVisitor; import org.jacoco.core.data.ExecutionDataStore; import org.jacoco.core.test.TargetLoader; /** * Scenario to measure the time taken by the instrumentation process itself. */ public class AnalysisTimeScenario extends TimedScenario { private final Class target; private final int count; protected AnalysisTimeScenario(Class target, int count) { super(String.format("analysing %s classes", Integer.valueOf(count))); this.target = target; this.count = count; } @Override protected Callable getInstrumentedCallable() throws Exception { final byte[] bytes = TargetLoader.getClassDataAsBytes(target); final ExecutionDataStore executionData = new ExecutionDataStore(); ICoverageVisitor visitor = new ICoverageVisitor() { public void visitCoverage(IClassCoverage coverage) { } }; final Analyzer analyzer = new Analyzer(executionData, visitor); return new Callable() { public Void call() throws Exception { for (int i = 0; i < count; i++) { analyzer.analyzeClass(bytes, target.getName()); } return null; } }; } } ExecuteInstrumentedCodeScenario.java000066400000000000000000000035571451257705100335370ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.perf; import java.util.concurrent.Callable; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.runtime.IRuntime; import org.jacoco.core.runtime.LoggerRuntime; import org.jacoco.core.runtime.RuntimeData; import org.jacoco.core.test.TargetLoader; /** * This scenario runs a given scenario twice and reports the execution time: * Once on its original version, once in a instrumented version. */ public class ExecuteInstrumentedCodeScenario extends TimedScenario { private final Class> target; protected ExecuteInstrumentedCodeScenario(String description, Class> target) { super(description); this.target = target; } @Override @SuppressWarnings("unchecked") protected Callable getInstrumentedCallable() throws Exception { IRuntime runtime = new LoggerRuntime(); runtime.startup(new RuntimeData()); final Instrumenter instr = new Instrumenter(runtime); final byte[] original = TargetLoader.getClassDataAsBytes(target); final byte[] instrumentedBuffer = instr.instrument(original, ""); final TargetLoader loader = new TargetLoader(); return (Callable) loader.add(target, instrumentedBuffer) .newInstance(); } @Override protected Callable getReferenceCallable() throws Exception { return target.newInstance(); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/IPerfOutput.java000066400000000000000000000027531451257705100275560ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.perf; /** * Interface to report performance figures to. */ public interface IPerfOutput { /** Indicator for no reference time given */ long NO_REFERENCE = Long.MIN_VALUE; /** * Reports the result of a time measurement with a optional reference time * for comparison. * * @param description * textual description of the test case * @param duration * duration in nano seconds * @param reference * optional reference time in nano seconds */ void writeTimeResult(String description, long duration, long reference); /** * Reports the result of a byte size measurement with a optional reference * size for comparison. * * @param description * textual description of the test case * @param size * size in bytes * @param reference * optional reference size in bytes */ void writeByteResult(String description, long size, long reference); } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/IPerfScenario.java000066400000000000000000000014661451257705100300210ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.perf; /** * Interface for a performance scenario. */ public interface IPerfScenario { /** * Runs the performance scenario and reports the result to the given * interface. * * @param output */ void run(IPerfOutput output) throws Exception; } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/InstrumentationSizeSzenario.java000066400000000000000000000026211451257705100330730ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.perf; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.runtime.IRuntime; import org.jacoco.core.runtime.LoggerRuntime; import org.jacoco.core.test.TargetLoader; /** * Scenario to measure the overhead in terms of additional byte code size * through instrumentation. */ public class InstrumentationSizeSzenario implements IPerfScenario { private final Class target; public InstrumentationSizeSzenario(Class target) { this.target = target; } public void run(IPerfOutput output) throws Exception { final IRuntime runtime = new LoggerRuntime(); final Instrumenter instr = new Instrumenter(runtime); final byte[] original = TargetLoader.getClassDataAsBytes(target); final byte[] instrumented = instr.instrument(original, ""); output.writeByteResult("instrumented class", instrumented.length, original.length); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/InstrumentationTimeScenario.java000066400000000000000000000030311451257705100330240ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.perf; import java.util.concurrent.Callable; import org.jacoco.core.instr.Instrumenter; import org.jacoco.core.runtime.LoggerRuntime; import org.jacoco.core.test.TargetLoader; /** * Scenario to measure the time taken by the instrumentation process itself. */ public class InstrumentationTimeScenario extends TimedScenario { private final Class target; private final int count; protected InstrumentationTimeScenario(Class target, int count) { super(String.format("instrumenting %s classes", Integer.valueOf(count))); this.target = target; this.count = count; } @Override protected Callable getInstrumentedCallable() throws Exception { final byte[] bytes = TargetLoader.getClassDataAsBytes(target); final Instrumenter instr = new Instrumenter(new LoggerRuntime()); return new Callable() { public Void call() throws Exception { for (int i = 0; i < count; i++) { instr.instrument(bytes, "TestTarget"); } return null; } }; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/PerfOutputWriter.java000066400000000000000000000050571451257705100306420ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.perf; import static java.lang.String.format; import java.io.PrintWriter; import org.jacoco.core.JaCoCo; /** * Formatted text output. */ public class PerfOutputWriter implements IPerfOutput { private final PrintWriter writer; public PerfOutputWriter(final PrintWriter writer) { this.writer = writer; writeHeader(); } private void writeHeader() { writer.printf("JaCoCo Performance Data%n%n"); writer.printf("JaCoCo Version: %s%n", JaCoCo.VERSION); writer.printf("JVM Vendor: %s%n", System.getProperty("java.vm.vendor")); writer.printf("JVM Version: %s%n%n", System.getProperty("java.vm.version")); writer.println( "scenario instr ref overhead"); writer.println( "----------------------------------------------------------"); } public void writeTimeResult(final String description, final long duration, final long reference) { final double dms = (double) duration / 1000000; if (reference == NO_REFERENCE) { writeResult(description, dms, "%.2f", "ms"); } else { final double rms = (double) reference / 1000000; writeResult(description, dms, rms, "%.2f", "ms"); } } public void writeByteResult(String description, long size, long reference) { if (size == 0) { return; } if (reference == NO_REFERENCE) { writeResult(description, size, "%.0f", "bytes"); } else { writeResult(description, size, reference, "%.0f", "bytes"); } } private void writeResult(final String description, final double subject, String fmt, String unit) { writer.printf("%-30s%8s %-6s%n", description, format(fmt, Double.valueOf(subject)), unit); } private void writeResult(final String description, final double subject, final double reference, String fmt, String unit) { double overhead = 100 * (subject - reference) / reference; writer.printf("%-30s%8s%8s %-6s%4.0f%%%n", description, format(fmt, Double.valueOf(subject)), format(fmt, Double.valueOf(reference)), unit, Double.valueOf(overhead)); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/PerformanceSuite.java000066400000000000000000000032341451257705100305760ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.perf; import java.io.PrintWriter; import org.jacoco.core.test.perf.targets.Target01; import org.jacoco.core.test.perf.targets.Target02; import org.jacoco.core.test.perf.targets.Target03; /** * The main test suite. */ public class PerformanceSuite implements IPerfScenario { public void run(IPerfOutput output) throws Exception { new ExecuteInstrumentedCodeScenario("plain method calls", Target01.class).run(output); new ExecuteInstrumentedCodeScenario("loop only", Target02.class) .run(output); new ExecuteInstrumentedCodeScenario("game of life", Target03.class) .run(output); new InstrumentationSizeSzenario(Target03.class).run(output); new InstrumentationTimeScenario(Target03.class, 1000).run(output); new AnalysisTimeScenario(Target03.class, 1000).run(output); } public static void main(String[] args) throws Exception { final PrintWriter writer; if (args.length == 0) { writer = new PrintWriter(System.out, true); } else { writer = new PrintWriter(args[0]); } IPerfOutput output = new PerfOutputWriter(writer); new PerformanceSuite().run(output); writer.close(); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/TimedScenario.java000066400000000000000000000037701451257705100300560ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.perf; import java.util.concurrent.Callable; /** * Base class for execution time test scenarios. */ public abstract class TimedScenario implements IPerfScenario { private static final int RUNS = 10; private final String description; protected TimedScenario(final String description) { this.description = description; } public void run(final IPerfOutput output) throws Exception { final long time = getMinimumTime(getInstrumentedCallable()); final Callable refRunnable = getReferenceCallable(); final long reftime; if (refRunnable == null) { reftime = IPerfOutput.NO_REFERENCE; } else { reftime = getMinimumTime(refRunnable); } output.writeTimeResult(description, time, reftime); } /** * Runs the given subject several times and returns the minimum execution * time. * * @param subject * @return minimum execution time in nano seconds * @throws Exception */ private long getMinimumTime(final Callable subject) throws Exception { long min = Long.MAX_VALUE; for (int i = 0; i < RUNS; i++) { final long t = getTime(subject); min = Math.min(min, t); } return min; } private long getTime(final Callable subject) throws Exception { long start = System.nanoTime(); subject.call(); return System.nanoTime() - start; } protected abstract Callable getInstrumentedCallable() throws Exception; protected Callable getReferenceCallable() throws Exception { return null; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/targets/000077500000000000000000000000001451257705100261275ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/targets/Target01.java000066400000000000000000000047741451257705100303750ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.perf.targets; import java.util.concurrent.Callable; /** * Plain method calls. */ public class Target01 implements Callable { @SuppressWarnings("unused") private int c; // 4 ^ 0 = 1 times public Void call() throws Exception { m1(); m1(); m1(); m1(); c++; // some side effect, otherwise the JIT will remove the method return null; } // 4 ^ 1 = 4 times public void m1() { m2(); m2(); m2(); m2(); c++; // some side effect, otherwise the JIT will remove the method } // 4 ^ 2 == 16 times public void m2() { m3(); m3(); m3(); m3(); c++; // some side effect, otherwise the JIT will remove the method } // 4 ^ 3 == 64 times public void m3() { m4(); m4(); m4(); m4(); c++; // some side effect, otherwise the JIT will remove the method } // 4 ^ 4 == 256 times public void m4() { m5(); m5(); m5(); m5(); c++; // some side effect, otherwise the JIT will remove the method } // 4 ^ 5 == 1,024 times public void m5() { m6(); m6(); m6(); m6(); c++; // some side effect, otherwise the JIT will remove the method } // 4 ^ 6 == 4,096 times public void m6() { m7(); m7(); m7(); m7(); c++; // some side effect, otherwise the JIT will remove the method } // 4 ^ 7 == 16,384 times public void m7() { m8(); m8(); m8(); m8(); c++; // some side effect, otherwise the JIT will remove the method } // 4 ^ 8 == 65,536 times public void m8() { m9(); m9(); m9(); m9(); c++; // some side effect, otherwise the JIT will remove the method } // 4 ^ 9 == 262,144 times public void m9() { m10(); m10(); m10(); m10(); c++; // some side effect, otherwise the JIT will remove the method } // 4 ^ 10 == 1,048,576 times public void m10() { m11(); m11(); m11(); m11(); c++; // some side effect, otherwise the JIT will remove the method } // 4 ^ 11 == 4,194,304 times public void m11() { c++; // some side effect, otherwise the JIT will remove the method } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/targets/Target02.java000066400000000000000000000015271451257705100303670ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.perf.targets; import java.util.concurrent.Callable; /** * Simple Loop. */ public class Target02 implements Callable { public Void call() throws Exception { @SuppressWarnings("unused") int count = 0; for (int i = 0; i < 10000000; i++) { count++; } return null; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/perf/targets/Target03.java000066400000000000000000000063571451257705100303760ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.perf.targets; import java.util.Random; import java.util.concurrent.Callable; /** * "Game of Life" implementation as a more reference scenario. Obviously the * implementation could be more elegant using several classes, but the test * runner targets one class only. Also one could think about more efficient * implementations which again is not the focus here. */ public class Target03 implements Callable { private final int width; private final int height; private boolean[][] field; public Target03(int width, int height) { this.width = width; this.height = height; this.field = createField(); } public Target03() { this(64, 64); } private boolean[][] createField() { boolean[][] f = new boolean[height][]; for (int i = 0; i < height; i++) { f[i] = new boolean[width]; } return f; } public void set(int x, int y, boolean flag) { field[wrap(x, width)][wrap(y, height)] = flag; } public boolean get(int x, int y) { return field[wrap(x, width)][wrap(y, height)]; } public void clear() { field = createField(); } public void randomFill(long seed, int count) { Random r = new Random(seed); for (int i = 0; i < count; i++) { set(r.nextInt(), r.nextInt(), true); } } public void tick() { boolean[][] next = createField(); for (int y = 0; y < height; y++) { for (int x = 0; x < width; x++) { final int n = getNeighbors(x, y); if (get(x, y)) { next[x][y] = 2 <= n && n <= 3; } else { next[x][y] = n == 3; } } } field = next; } // Neighbor private int getNeighbors(int x, int y) { int count = 0; if (get(x - 1, y - 1)) { count++; } if (get(x + 0, y - 1)) { count++; } if (get(x + 1, y - 1)) { count++; } if (get(x + 1, y + 0)) { count++; } if (get(x + 1, y + 1)) { count++; } if (get(x + 0, y + 1)) { count++; } if (get(x - 1, y + 1)) { count++; } if (get(x - 1, y + 0)) { count++; } return count; } private int wrap(int value, int size) { int res = value % size; if (res < 0) { res += size; } return res; } @Override public String toString() { StringBuilder sb = new StringBuilder(); for (int y = 0; y < height; y++) { for (int x = 0; x < width; x++) { sb.append(get(x, y) ? 'O' : '.'); } sb.append('\n'); } return sb.toString(); } public Void call() throws Exception { clear(); randomFill(123, width * height / 2); for (int i = 0; i < 20; i++) { tick(); } return null; } // Demo public static void main(String[] args) { Target03 t = new Target03(10, 10); t.randomFill(123, 20); for (int i = 0; i < 10; i++) { System.out.println("Generation " + i + ":"); System.out.println(t); t.tick(); } } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/validation/000077500000000000000000000000001451257705100256545ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/validation/Compiler.java000066400000000000000000000020241451257705100302670ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation; /** * Provides ability to detect compiler based on difference in generated bytecode * for switch by enum. */ enum Compiler { DETECT; /** * @return true if this file was compiled by javac */ boolean isJDK() { switch (DETECT) { default: try { Compiler.class.getDeclaredField("$SWITCH_TABLE$" + Compiler.class.getName().replace('.', '$')); return false; } catch (NoSuchFieldException e) { return true; } } } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/validation/JavaVersion.java000066400000000000000000000040531451257705100307500ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation; /** * Parsed value of "java.version" system property. */ public final class JavaVersion { private final int feature; private final int update; /** * @param javaVersionPropertyValue * value of "java.version" property * @see System#getProperties() description of properties */ JavaVersion(final String javaVersionPropertyValue) { final String[] s = javaVersionPropertyValue.split("[._-]"); if ("1".equals(s[0])) { this.feature = Integer.parseInt(s[1]); this.update = s.length > 3 ? Integer.parseInt(s[3]) : 0; } else { this.feature = Integer.parseInt(s[0]); this.update = s.length > 2 ? Integer.parseInt(s[2]) : 0; } } /** * @return value of feature-release counter, for example: 8 for version * "1.8.0_152" and 9 for version "9.0.1" */ int feature() { return feature; } /** * @return value of update-release counter, for example: 152 for version * "1.8.0_152" and 1 for version "9.0.1" */ int update() { return update; } /** * @param version * version to compare with * @return true if this version is less than given */ public boolean isBefore(final String version) { final JavaVersion other = new JavaVersion(version); return this.feature < other.feature || (this.feature == other.feature && this.update < other.update); } /** * @return version of the current JVM */ public static JavaVersion current() { return new JavaVersion(System.getProperty("java.version")); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/validation/JavaVersionTest.java000066400000000000000000000034061451257705100316110ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation; import org.junit.Test; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; public class JavaVersionTest { @Test public void should_parse_values_of_java_version_property() { JavaVersion v; v = new JavaVersion("1.8.0_162"); assertEquals(8, v.feature()); assertEquals(162, v.update()); v = new JavaVersion("1.8.0_172-ea"); assertEquals(8, v.feature()); assertEquals(172, v.update()); v = new JavaVersion("9"); assertEquals(9, v.feature()); assertEquals(0, v.update()); v = new JavaVersion("9.0.1"); assertEquals(9, v.feature()); assertEquals(1, v.update()); v = new JavaVersion("10-ea"); assertEquals(10, v.feature()); assertEquals(0, v.update()); } @Test public void should_compare_with_given_version() { assertTrue(new JavaVersion("1.7.0_80").isBefore("1.8.0_92")); assertTrue(new JavaVersion("1.8.0_31").isBefore("1.8.0_92")); assertFalse(new JavaVersion("1.8.0_92").isBefore("1.8.0_92")); assertFalse(new JavaVersion("1.8.0_162").isBefore("1.8.0_92")); assertFalse(new JavaVersion("1.8.0_162").isBefore("1.8")); assertFalse(new JavaVersion("9.0.1").isBefore("1.8.0_92")); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/validation/Source.java000066400000000000000000000106501451257705100277610ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation; import java.io.BufferedReader; import java.io.FileInputStream; import java.io.IOException; import java.io.InputStreamReader; import java.io.Reader; import java.util.ArrayList; import java.util.Collection; import java.util.Collections; import java.util.List; import java.util.regex.Matcher; import java.util.regex.Pattern; import org.jacoco.core.analysis.IBundleCoverage; import org.jacoco.core.analysis.IClassCoverage; import org.jacoco.core.analysis.ICoverageNode; import org.jacoco.core.analysis.ILine; import org.jacoco.core.analysis.IPackageCoverage; import org.jacoco.core.analysis.ISourceFileCoverage; /** * Reads a single source file and allows access to its line coverage. */ public class Source { private static final String SRC_LOCATION = "src/"; private static final String SRC_ENCODING = "UTF-8"; private static final Pattern COMMENT_PATTERN = Pattern .compile("(?null */ public String getComment() { final Matcher matcher = COMMENT_PATTERN.matcher(text); return matcher.find() ? matcher.group(1) : null; } @Override public String toString() { return Source.this.coverage.getName() + ":" + nr; } } private final List lines; private final ISourceFileCoverage coverage; /** * Reads a source file from the given reader. * * @param reader * the reader to read from, will be closed * @param coverage * corresponding coverage data * @throws IOException * if an I/O error occurs */ public Source(final Reader reader, ISourceFileCoverage coverage) throws IOException { this.lines = new ArrayList(); this.coverage = coverage; final BufferedReader buffer = new BufferedReader(reader); int nr = 1; for (String l = buffer.readLine(); l != null; l = buffer.readLine()) { lines.add(new Line(nr, l, coverage.getLine(nr))); nr++; } buffer.close(); } /** * @return all lines of the source file */ public List getLines() { return Collections.unmodifiableList(lines); } /** * @return the corresponding coverage node */ public ISourceFileCoverage getCoverage() { return coverage; } /** * Loads the source file which holds the given target class. * * @param target * the target class we want the source for * @param bundle * the bundle containing the analyzed class and its source file * @return a {@link Source} instance */ public static Source load(Class target, IBundleCoverage bundle) throws IOException { final IPackageCoverage pkgCov = findByName(bundle.getPackages(), vm(target.getPackage().getName())); final IClassCoverage clsCov = findByName(pkgCov.getClasses(), vm(target.getName())); final ISourceFileCoverage srcCov = findByName(pkgCov.getSourceFiles(), clsCov.getSourceFileName()); return new Source(open(SRC_LOCATION + pkgCov.getName() + "/" + clsCov.getSourceFileName()), srcCov); } private static T findByName(Collection nodes, String name) { for (T node : nodes) { if (name.equals(node.getName())) { return node; } } throw new AssertionError("Node not found: " + name); } private static String vm(String javaname) { return javaname.replace('.', '/'); } private static Reader open(String file) throws IOException { return new InputStreamReader(new FileInputStream(file), SRC_ENCODING); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/validation/SourceTest.java000066400000000000000000000103741451257705100306240ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNull; import java.io.IOException; import java.io.StringReader; import java.util.List; import org.jacoco.core.internal.analysis.CounterImpl; import org.jacoco.core.internal.analysis.SourceFileCoverageImpl; import org.jacoco.core.test.validation.Source.Line; import org.junit.Test; /** * Unit tests for {@link Source}. */ public class SourceTest { @Test public void should_parse_lines() throws IOException { String src = "aaa\nbbb\n;"; final Source s = new Source(new StringReader(src), new SourceFileCoverageImpl("Foo", "foo")); List lines = s.getLines(); assertEquals(3, lines.size()); assertEquals("aaa", lines.get(0).getText()); assertEquals("bbb", lines.get(1).getText()); assertEquals(";", lines.get(2).getText()); } @Test public void should_parse_empty_lines() throws IOException { String src = "\naaa\n\nbbb\n"; final Source s = new Source(new StringReader(src), new SourceFileCoverageImpl("Foo", "foo")); List lines = s.getLines(); assertEquals(4, lines.size()); assertEquals("", lines.get(0).getText()); assertEquals("aaa", lines.get(1).getText()); assertEquals("", lines.get(2).getText()); assertEquals("bbb", lines.get(3).getText()); } @Test public void should_parse_crnl_separator() throws IOException { String src = "aaa\r\nbbb"; final Source s = new Source(new StringReader(src), new SourceFileCoverageImpl("Foo", "foo")); List lines = s.getLines(); assertEquals(2, lines.size()); assertEquals("aaa", lines.get(0).getText()); assertEquals("bbb", lines.get(1).getText()); } @Test public void should_calculate_line_numbers() throws IOException { String src = "a\nb\nc"; final Source s = new Source(new StringReader(src), new SourceFileCoverageImpl("Foo", "foo")); List lines = s.getLines(); assertEquals(3, lines.size()); assertEquals(1, lines.get(0).getNr()); assertEquals(2, lines.get(1).getNr()); assertEquals(3, lines.get(2).getNr()); } @Test public void line_should_implement_toString() throws IOException { String src = "a\nb"; final Source s = new Source(new StringReader(src), new SourceFileCoverageImpl("Foo", "foo")); List lines = s.getLines(); assertEquals(2, lines.size()); assertEquals("Foo:1", lines.get(0).toString()); assertEquals("Foo:2", lines.get(1).toString()); } @Test public void line_should_provide_corresponding_coverage() throws IOException { String src = "a\nb\nc"; SourceFileCoverageImpl sc = new SourceFileCoverageImpl("Foo", "foo"); sc.increment(CounterImpl.getInstance(1, 0), CounterImpl.COUNTER_0_0, 1); sc.increment(CounterImpl.getInstance(2, 0), CounterImpl.COUNTER_0_0, 2); sc.increment(CounterImpl.getInstance(3, 0), CounterImpl.COUNTER_0_0, 3); final Source s = new Source(new StringReader(src), sc); List lines = s.getLines(); assertEquals(3, lines.size()); assertEquals(1, lines.get(0).getCoverage().getInstructionCounter() .getMissedCount()); assertEquals(2, lines.get(1).getCoverage().getInstructionCounter() .getMissedCount()); assertEquals(3, lines.get(2).getCoverage().getInstructionCounter() .getMissedCount()); } @Test public void line_should_return_comment() throws IOException { String src = "aaa\nbbb // test()\n}//nospaces()\n/* http://jacoco.org/ */"; final Source s = new Source(new StringReader(src), new SourceFileCoverageImpl("Foo", "foo")); List lines = s.getLines(); assertEquals(4, lines.size()); assertNull(lines.get(0).getComment()); assertEquals(" test()", lines.get(1).getComment()); assertEquals("nospaces()", lines.get(2).getComment()); assertNull(lines.get(3).getComment()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/validation/StatementExecutor.java000066400000000000000000000040511451257705100322020ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation; import java.lang.reflect.InvocationTargetException; /** * Executes statements against a given Java object instance. */ class StatementExecutor implements StatementParser.IStatementVisitor { private final Object target; private final Object[] prefixArgs; StatementExecutor(Object target, Object... prefixArgs) { this.target = target; this.prefixArgs = prefixArgs; } public void visitInvocation(String ctx, String name, Object... args) { args = concat(prefixArgs, args); try { target.getClass().getMethod(name, getTypes(args)).invoke(target, args); } catch (InvocationTargetException e) { Throwable te = e.getTargetException(); if (te instanceof AssertionError) { throw (AssertionError) te; } throw new RuntimeException("Invocation error (" + ctx + ")", te); } catch (Exception e) { throw new RuntimeException("Invocation error (" + ctx + ")", e); } } private static Object[] concat(Object[] a, Object[] b) { final Object[] result = new Object[a.length + b.length]; System.arraycopy(a, 0, result, 0, a.length); System.arraycopy(b, 0, result, a.length, b.length); return result; } private static Class[] getTypes(Object[] instances) { final Class[] classes = new Class[instances.length]; for (int i = 0; i < instances.length; i++) { Class c = instances[i].getClass(); if (c == Integer.class) { // We always use primitive int parameters: c = Integer.TYPE; } classes[i] = c; } return classes; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/validation/StatementExecutorTest.java000066400000000000000000000056731451257705100330550ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation; import static org.junit.Assert.assertEquals; import static org.junit.Assert.fail; import java.io.IOException; import java.util.Arrays; import java.util.HashMap; import java.util.List; import java.util.Map; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link StatementExecutor}. */ public class StatementExecutorTest { private Map> invocations; @Before public void setup() { invocations = new HashMap>(); } @Test public void should_prefix_arguments() { StatementExecutor executor = new StatementExecutor(this, "Hello", "world"); executor.visitInvocation("ctx", "target1", "!"); assertEquals(Arrays.asList("Hello", "world", "!"), invocations.get("target1")); } @Test public void should_call_method_with_int_argument() { StatementExecutor executor = new StatementExecutor(this); executor.visitInvocation("ctx", "target2", Integer.valueOf(42)); assertEquals(Arrays.asList(Integer.valueOf(42)), invocations.get("target2")); } @Test public void should_preserve_AssertionError() { StatementExecutor executor = new StatementExecutor(this); try { executor.visitInvocation("ctx", "target3"); fail("exception expected"); } catch (AssertionError e) { assertEquals("Original AssertionError.", e.getMessage()); } } @Test public void should_wrap_other_exceptions() { StatementExecutor executor = new StatementExecutor(this); try { executor.visitInvocation("ctx", "target4"); fail("exception expected"); } catch (RuntimeException e) { assertEquals("Invocation error (ctx)", e.getMessage()); assertEquals("Original IOException.", e.getCause().getMessage()); } } @Test public void should_throw_RuntimeException_when_method_cannot_be_invoked() { StatementExecutor executor = new StatementExecutor(this); try { executor.visitInvocation("ctx", "doesNotExist"); fail("exception expected"); } catch (RuntimeException e) { assertEquals("Invocation error (ctx)", e.getMessage()); } } public void target1(String a, String b, String c) { invocations.put("target1", Arrays.asList(a, b, c)); } public void target2(int i) { invocations.put("target2", Arrays.asList(Integer.valueOf(i))); } public void target3() { throw new AssertionError("Original AssertionError."); } public void target4() throws IOException { throw new IOException("Original IOException."); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/validation/StatementParser.java000066400000000000000000000065221451257705100316450ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation; import java.io.IOException; import java.io.StreamTokenizer; import java.io.StringReader; import java.util.ArrayList; import java.util.List; /** * Simple parser for Java like method invocation statements. For example: * *
 * foo("BAR", 42)
 * 
* * Method parameters can only be String or int literals. */ class StatementParser { /** * Call-back interface for parsed statements. */ public interface IStatementVisitor { /** * Called when a method invocation has been paresed. * * @param ctx * context information for error messages * @param name * local method name * @param args * argument values */ void visitInvocation(String ctx, String name, Object... args); } /** * Parses the given source. * * @param source * source string to parse * @param visitor * visitor to emit parsed statements * @param ctx * context information to include in error messages */ public static void parse(String source, IStatementVisitor visitor, String ctx) throws IOException { new StatementParser(source, visitor, ctx).parse(); } private final IStatementVisitor visitor; private final StreamTokenizer tokenizer; private final String ctx; private StatementParser(String source, IStatementVisitor visitor, String ctx) { this.visitor = visitor; this.ctx = ctx; tokenizer = new StreamTokenizer(new StringReader(source)); tokenizer.resetSyntax(); tokenizer.whitespaceChars(' ', ' '); tokenizer.whitespaceChars('\t', '\t'); tokenizer.wordChars('a', 'z'); tokenizer.wordChars('A', 'Z'); tokenizer.quoteChar('"'); tokenizer.parseNumbers(); } private void parse() throws IOException { while (!accept(StreamTokenizer.TT_EOF)) { invocation(); } } private void invocation() throws IOException { final String name = expect(StreamTokenizer.TT_WORD).sval; final List args = new ArrayList(); expect('('); if (!accept(')')) { args.add(argument()); while (!accept(')')) { expect(','); args.add(argument()); } } visitor.visitInvocation(ctx, name, args.toArray()); } private Object argument() throws IOException { if (accept(StreamTokenizer.TT_NUMBER)) { return Integer.valueOf((int) tokenizer.nval); } if (accept('"')) { return tokenizer.sval; } throw syntaxError(); } private boolean accept(final int type) throws IOException { final boolean match = tokenizer.nextToken() == type; if (!match) { tokenizer.pushBack(); } return match; } private StreamTokenizer expect(final int type) throws IOException { if (tokenizer.nextToken() != type) { throw syntaxError(); } return tokenizer; } private IOException syntaxError() { return new IOException("Invalid syntax (" + ctx + ")"); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/validation/StatementParserTest.java000066400000000000000000000102301451257705100324740ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation; import static org.junit.Assert.assertEquals; import static org.junit.Assert.fail; import java.io.IOException; import java.util.ArrayList; import java.util.Arrays; import java.util.List; import org.jacoco.core.test.validation.StatementParser.IStatementVisitor; import org.junit.After; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link StatementParser} */ public class StatementParserTest { private IStatementVisitor visitor; private List actualInvocations; private List expectedInvocations; @Before public void setup() { actualInvocations = new ArrayList(); expectedInvocations = new ArrayList(); visitor = new IStatementVisitor() { public void visitInvocation(String ctx, String name, Object... args) { actualInvocations.add(invocationStr(ctx, name, args)); } }; } @After public void teardown() { assertEquals(expectedInvocations, actualInvocations); } @Test public void should_parse_empty_string() throws IOException { StatementParser.parse("", visitor, "Foo.java"); } @Test public void should_parse_invocation_without_params() throws IOException { StatementParser.parse("run()", visitor, "Foo.java"); expectInvocation("Foo.java", "run"); } @Test public void should_parse_invocation_with_one_int_parameter() throws IOException { StatementParser.parse("ask(42)", visitor, "Foo.java"); expectInvocation("Foo.java", "ask", Integer.valueOf(42)); } @Test public void should_parse_invocation_with_one_string_parameter() throws IOException { StatementParser.parse("say(\"hello\")", visitor, "Foo.java"); expectInvocation("Foo.java", "say", "hello"); } @Test public void should_parse_invocation_with_two_parameters() throws IOException { StatementParser.parse("add(1000, 234)", visitor, "Foo.java"); expectInvocation("Foo.java", "add", Integer.valueOf(1000), Integer.valueOf(234)); } @Test public void should_parse_invocation_with_mixed_parameter_types() throws IOException { StatementParser.parse("mix(1, \"two\", 3)", visitor, "Foo.java"); expectInvocation("Foo.java", "mix", Integer.valueOf(1), "two", Integer.valueOf(3)); } @Test public void should_parse_multiple_invocations() throws IOException { StatementParser.parse("start() stop()", visitor, "Foo.java"); expectInvocation("Foo.java", "start"); expectInvocation("Foo.java", "stop"); } @Test public void should_fail_when_parenthesis_is_missing() throws IOException { try { StatementParser.parse("bad(", visitor, "Foo.java"); fail("exception expected"); } catch (IOException e) { // expected } } @Test public void should_fail_when_argument1_is_missing() throws IOException { try { StatementParser.parse("bad(,2)", visitor, "Foo.java"); fail("exception expected"); } catch (IOException e) { // expected } } @Test public void should_fail_when_argument2_is_missing() throws IOException { try { StatementParser.parse("bad(1,)", visitor, "Foo.java"); fail("exception expected"); } catch (IOException e) { // expected } } @Test public void should_give_context_info_when_parsing_fails() throws IOException { try { StatementParser.parse("bad", visitor, "Foo.java:32"); fail("exception expected"); } catch (IOException e) { assertEquals("Invalid syntax (Foo.java:32)", e.getMessage()); } } private void expectInvocation(String ctx, String name, Object... args) { expectedInvocations.add(invocationStr(ctx, name, args)); } private String invocationStr(String ctx, String name, Object... args) { return String.format("%s:%s%s", ctx, name, Arrays.asList(args)); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/validation/ValidationTestBase.java000066400000000000000000000157231451257705100322540ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; import java.io.IOException; import java.lang.reflect.Method; import java.util.Arrays; import org.jacoco.core.analysis.Analyzer; import org.jacoco.core.analysis.CoverageBuilder; import org.jacoco.core.analysis.ICounter; import org.jacoco.core.analysis.ILine; import org.jacoco.core.data.ExecutionData; import org.jacoco.core.data.ExecutionDataStore; import org.jacoco.core.internal.analysis.CounterImpl; import org.jacoco.core.test.InstrumentingLoader; import org.jacoco.core.test.TargetLoader; import org.jacoco.core.test.validation.Source.Line; import org.jacoco.core.test.validation.targets.Stubs; import org.junit.Before; import org.junit.Test; /** * Base class for validation tests. It executes the given class under code * coverage and provides the coverage results for validation. */ public abstract class ValidationTestBase { protected static final boolean isJDKCompiler = Compiler.DETECT.isJDK(); private static final String[] STATUS_NAME = new String[4]; { STATUS_NAME[ICounter.EMPTY] = "EMPTY"; STATUS_NAME[ICounter.NOT_COVERED] = "NOT_COVERED"; STATUS_NAME[ICounter.FULLY_COVERED] = "FULLY_COVERED"; STATUS_NAME[ICounter.PARTLY_COVERED] = "PARTLY_COVERED"; } private final Class target; private Source source; private InstrumentingLoader loader; protected ValidationTestBase(final Class target) { this.target = target; } @Before public void setup() throws Exception { final ExecutionDataStore store = execute(); analyze(store); } private ExecutionDataStore execute() throws Exception { loader = new InstrumentingLoader(target); loader.setDefaultAssertionStatus(true); run(loader.loadClass(target.getName())); return loader.collect(); } protected void run(final Class targetClass) throws Exception { targetClass.getMethod("main", String[].class).invoke(null, (Object) new String[0]); } private void analyze(final ExecutionDataStore store) throws IOException { final CoverageBuilder builder = new CoverageBuilder(); final Analyzer analyzer = new Analyzer(store, builder); for (ExecutionData data : store.getContents()) { analyze(analyzer, data); } source = Source.load(target, builder.getBundle("Test")); } private void analyze(final Analyzer analyzer, final ExecutionData data) throws IOException { final byte[] bytes = TargetLoader .getClassDataAsBytes(target.getClassLoader(), data.getName()); analyzer.analyzeClass(bytes, data.getName()); } /** * All single line comments are interpreted as statements in the following * format: * *
	 * // statement1() statement2()
	 * 
*/ @Test public void execute_assertions_in_comments() throws IOException { for (Line line : source.getLines()) { String exec = line.getComment(); if (exec != null) { StatementParser.parse(exec, new StatementExecutor(this, line), line.toString()); } } } /** * Source files for validation tests should contain the license header, * which can not contain executable lines, so this test allows to catch * cases when the compiler generates wrong line numbers. */ @Test public void first_line_in_coverage_data_should_be_greater_than_one() { assertTrue("First line in coverage data should be greater than one", 1 < source.getCoverage().getFirstLine()); } @Test public void last_line_in_coverage_data_should_be_less_or_equal_to_number_of_lines_in_source_file() { assertTrue(String.format( "Last line in coverage data (%d) should be less or equal to number of lines in source file (%d)", Integer.valueOf(source.getCoverage().getLastLine()), Integer.valueOf(source.getLines().size())), source.getCoverage().getLastLine() <= source.getLines().size()); } @Test public void all_missed_instructions_should_have_line_number() { CounterImpl c = CounterImpl.COUNTER_0_0; for (Line line : source.getLines()) { c = c.increment(line.getCoverage().getInstructionCounter()); } assertEquals( "sum of missed instructions of all lines should be equal to missed instructions of file", source.getCoverage().getInstructionCounter().getMissedCount(), c.getMissedCount()); } @Test public void all_branches_should_have_line_number() { CounterImpl c = CounterImpl.COUNTER_0_0; for (Line line : source.getLines()) { c = c.increment(line.getCoverage().getBranchCounter()); } assertEquals( "sum of branch counters of all lines should be equal to branch counter of file", source.getCoverage().getBranchCounter(), c); } /* * Predefined assertion methods: */ private void assertCoverage(final Line line, final int insnStatus, final int missedBranches, final int coveredBranches) { final ILine coverage = line.getCoverage(); String msg = String.format("Instructions (%s)", line); final int actualStatus = coverage.getInstructionCounter().getStatus(); assertEquals(msg, STATUS_NAME[insnStatus], STATUS_NAME[actualStatus]); msg = String.format("Branches (%s)", line); assertEquals(msg, CounterImpl.getInstance(missedBranches, coveredBranches), coverage.getBranchCounter()); } public void assertFullyCovered(final Line line, final int missedBranches, final int coveredBranches) { assertCoverage(line, ICounter.FULLY_COVERED, missedBranches, coveredBranches); } public void assertFullyCovered(final Line line) { assertFullyCovered(line, 0, 0); } public void assertPartlyCovered(final Line line, final int missedBranches, final int coveredBranches) { assertCoverage(line, ICounter.PARTLY_COVERED, missedBranches, coveredBranches); } public void assertPartlyCovered(final Line line) { assertPartlyCovered(line, 0, 0); } public void assertNotCovered(final Line line, final int missedBranches, final int coveredBranches) { assertCoverage(line, ICounter.NOT_COVERED, missedBranches, coveredBranches); } public void assertNotCovered(final Line line) { assertNotCovered(line, 0, 0); } public void assertEmpty(final Line line) { assertCoverage(line, ICounter.EMPTY, 0, 0); } protected void assertLogEvents(String... events) throws Exception { final Method getter = Class .forName(Stubs.class.getName(), false, loader) .getMethod("getLogEvents"); assertEquals("Log events", Arrays.asList(events), getter.invoke(null)); } protected void assertMethodCount(final int expectedTotal) { assertEquals(expectedTotal, source.getCoverage().getMethodCounter().getTotalCount()); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/validation/targets/000077500000000000000000000000001451257705100273255ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/test/validation/targets/Stubs.java000066400000000000000000000055701451257705100312770ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.test.validation.targets; import java.util.ArrayList; import java.util.List; /** * Collection of stub methods that are called from the coverage targets. * */ public class Stubs { /** * Exception stub. */ public static class StubException extends RuntimeException { static final long serialVersionUID = 0L; } /** * Superclass stub. */ public static class SuperClass { public SuperClass(boolean arg) { } } /** * Enum stub. */ public static enum Enum { A, B, C } /** * Dummy method. */ public static void nop() { } /** * Dummy method. */ public static void nop(int i) { } /** * Dummy method. */ public static void nop(boolean b) { } /** * Dummy method. */ public static void nop(Object o) { } /** * @return always true */ public static boolean t() { return true; } /** * @return always false */ public static boolean f() { return false; } /** * @return always 1 */ public static int i1() { return 1; } /** * @return always 3 */ public static int i2() { return 2; } /** * @return always 3 */ public static int i3() { return 3; } /** * @return always A */ public static Enum enumA() { return Enum.A; } /** * Always throws a {@link RuntimeException}. * * @throws StubException * always thrown */ public static void ex() throws StubException { throw new StubException(); } /** * Throws a {@link RuntimeException} if given argument is true. */ public static void ex(boolean t) { if (t) { throw new StubException(); } } /** * Directly executes the given runnable. */ public static void exec(Runnable task) { task.run(); } /** * Never executes the given runnable. */ public static void noexec(Runnable task) { } /** * List of logged events. Using a static member here works as this class is * loaded in a new class loader for every test case. */ private static List events = new ArrayList(); /** * Records a event with the given id for later verification. */ public static void logEvent(String id) { events.add(id); } /** * Returns a list of all recorded events in the sequence of recording. */ public static List getLogEvents() { return events; } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/tools/000077500000000000000000000000001451257705100237035ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/tools/ExecDumpClientTest.java000066400000000000000000000125161451257705100302640ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.tools; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.io.IOException; import java.io.InputStream; import java.net.ConnectException; import java.net.InetAddress; import java.net.ServerSocket; import java.net.Socket; import java.util.ArrayList; import java.util.Arrays; import java.util.List; import org.jacoco.core.data.SessionInfo; import org.jacoco.core.runtime.IRemoteCommandVisitor; import org.jacoco.core.runtime.RemoteControlReader; import org.jacoco.core.runtime.RemoteControlWriter; import org.junit.After; import org.junit.Before; import org.junit.Test; /** * Unit tests for {@link ExecDumpClient}. */ public class ExecDumpClientTest { private ExecDumpClient client; private List callbacks; private boolean dumpRequested; private boolean resetRequested; private ServerSocket server; @Before public void setup() { callbacks = new ArrayList(); client = new ExecDumpClient() { @Override protected void onConnecting(InetAddress address, int port) { callbacks.add("onConnecting"); } @Override protected void onConnectionFailure(IOException exception) { callbacks.add("onConnectionFailure"); } }; } @After public void teardown() throws IOException { if (server != null) { server.close(); } } @Test public void testNoRetries() throws IOException { try { client.dump((String) null, getFreePort()); fail("ConnectException expected"); } catch (ConnectException e) { // expected } assertEquals(Arrays.asList("onConnecting"), callbacks); } @Test public void testWithRetries() throws IOException { client.setRetryCount(3); client.setRetryDelay(0); try { client.dump((String) null, getFreePort()); fail("ConnectException expected"); } catch (ConnectException e) { // expected } assertEquals(Arrays.asList( // Initial attempt "onConnecting", // 1. Retry "onConnectionFailure", "onConnecting", // 2. Retry "onConnectionFailure", "onConnecting", // 3. Retry "onConnectionFailure", "onConnecting") , callbacks); } @Test public void testDump() throws IOException { int port = createExecServer(); ExecFileLoader loader = client.dump((String) null, port); assertTrue(dumpRequested); assertFalse(resetRequested); List infos = loader.getSessionInfoStore().getInfos(); assertEquals(1, infos.size()); assertEquals("TestId", infos.get(0).getId()); } @Test public void testReset() throws IOException { int port = createExecServer(); client.setDump(false); client.setReset(true); client.dump((String) null, port); assertFalse(dumpRequested); assertTrue(resetRequested); } @Test public void should_throw_IOException_when_server_closes_connection_without_response() throws IOException { int port = createNopServer(); try { client.dump((String) null, port); fail("exception expected"); } catch (IOException e) { assertEquals("Socket closed unexpectedly.", e.getMessage()); } } private int getFreePort() throws IOException { final ServerSocket server = new ServerSocket(0, 0, InetAddress.getByName(null)); final int port = server.getLocalPort(); server.close(); return port; } private int createExecServer() throws IOException { server = new ServerSocket(0, 0, InetAddress.getByName(null)); new Thread(new Runnable() { public void run() { try { handleConnection(server.accept()); } catch (IOException e) { // ignore } } }).start(); return server.getLocalPort(); } private void handleConnection(Socket socket) throws IOException { final RemoteControlWriter writer = new RemoteControlWriter( socket.getOutputStream()); final RemoteControlReader reader = new RemoteControlReader( socket.getInputStream()); reader.setRemoteCommandVisitor(new IRemoteCommandVisitor() { public void visitDumpCommand(boolean dump, boolean reset) throws IOException { dumpRequested = dump; resetRequested = reset; if (dump) { writer.visitSessionInfo( new SessionInfo("TestId", 100, 200)); } writer.sendCmdOk(); } }); reader.read(); } private int createNopServer() throws IOException { server = new ServerSocket(0, 0, InetAddress.getByName(null)); new Thread(new Runnable() { public void run() { try { Socket socket = server.accept(); InputStream in = socket.getInputStream(); // Read Header: in.read(); in.read(); in.read(); in.read(); in.read(); // Read Dump Command: in.read(); in.read(); in.read(); // Then just close connection without any response: socket.close(); } catch (IOException e) { // ignore } } }).start(); return server.getLocalPort(); } } jacoco-0.8.11/org.jacoco.core.test/src/org/jacoco/core/tools/ExecFileLoaderTest.java000066400000000000000000000110661451257705100302250ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.tools; import static org.junit.Assert.assertEquals; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.FileWriter; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.util.List; import org.jacoco.core.data.ExecutionData; import org.jacoco.core.data.ExecutionDataReader; import org.jacoco.core.data.ExecutionDataStore; import org.jacoco.core.data.ExecutionDataWriter; import org.jacoco.core.data.SessionInfo; import org.jacoco.core.data.SessionInfoStore; import org.junit.Before; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TemporaryFolder; /** * Unit tests for {@link ExecFileLoader}. */ public class ExecFileLoaderTest { @Rule public final TemporaryFolder sourceFolder = new TemporaryFolder(); private ExecFileLoader loader; @Before public void setup() { loader = new ExecFileLoader(); } @Test public void testLoadFile() throws IOException { loader.load(createFile("a")); loader.load(createFile("bb")); assertLoaderContents("a", "bb"); } @Test public void testLoadInputStream() throws IOException { final FileInputStream in1 = new FileInputStream(createFile("a")); loader.load(in1); in1.close(); final FileInputStream in2 = new FileInputStream(createFile("bb")); loader.load(in2); in2.close(); assertLoaderContents("a", "bb"); } @Test(expected = IOException.class) public void testLoadBrokenContent() throws IOException { final File file = new File(sourceFolder.getRoot(), "broken.exec"); final FileWriter writer = new FileWriter(file); writer.write("Invalid Content"); writer.close(); loader.load(file); } @Test public void testSaveFile() throws IOException { final File file = new File(sourceFolder.getRoot(), "target.exec"); // Write invalid data to ensure the file is actually overwritten: final OutputStream out = new FileOutputStream(file); out.write("invalid".getBytes()); out.close(); loader.load(createFile("a")); loader.save(file, false); assertFileContents(file, "a"); } @Test public void testSaveFileAppend() throws IOException { final File file = createFile("a"); loader.load(createFile("bb")); loader.save(file, true); assertFileContents(file, "a", "bb"); } @Test public void testCreateSubfolders() throws IOException { final File file = new File(sourceFolder.getRoot(), "a/b/c/target.exec"); loader.load(createFile("a")); loader.save(file, true); assertFileContents(file, "a"); } private File createFile(String id) throws IOException { final File file = new File(sourceFolder.getRoot(), id + ".exec"); final FileOutputStream out = new FileOutputStream(file); final ExecutionDataWriter writer = new ExecutionDataWriter(out); final int value = id.length(); writer.visitClassExecution( new ExecutionData(value, id, new boolean[] { true })); writer.visitSessionInfo(new SessionInfo(id, value, value)); out.close(); return file; } private void assertLoaderContents(String... expected) { assertContents(loader.getExecutionDataStore(), loader.getSessionInfoStore(), expected); } private void assertFileContents(File file, String... expected) throws IOException { final InputStream in = new FileInputStream(file); final ExecutionDataStore execStore = new ExecutionDataStore(); final SessionInfoStore sessionStore = new SessionInfoStore(); final ExecutionDataReader reader = new ExecutionDataReader(in); reader.setExecutionDataVisitor(execStore); reader.setSessionInfoVisitor(sessionStore); reader.read(); assertContents(execStore, sessionStore, expected); } private void assertContents(ExecutionDataStore execStore, SessionInfoStore sessionStore, String... expected) { final List infos = sessionStore.getInfos(); assertEquals(expected.length, execStore.getContents().size()); assertEquals(expected.length, infos.size()); int idx = 0; for (String id : expected) { assertEquals(id, execStore.get(id.length()).getName()); assertEquals(id, infos.get(idx++).getId()); } } } jacoco-0.8.11/org.jacoco.core/000077500000000000000000000000001451257705100160215ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core/.classpath000066400000000000000000000014151451257705100200050ustar00rootroot00000000000000 jacoco-0.8.11/org.jacoco.core/.project000066400000000000000000000010671451257705100174740ustar00rootroot00000000000000 org.jacoco.core org.eclipse.jdt.core.javabuilder org.eclipse.m2e.core.maven2Builder org.eclipse.m2e.core.maven2Nature org.eclipse.jdt.core.javanature jacoco-0.8.11/org.jacoco.core/.settings/000077500000000000000000000000001451257705100177375ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core/.settings/org.eclipse.core.resources.prefs000066400000000000000000000001121451257705100261440ustar00rootroot00000000000000eclipse.preferences.version=1 encoding/=UTF-8 encoding/src=UTF-8 jacoco-0.8.11/org.jacoco.core/.settings/org.eclipse.jdt.core.prefs000066400000000000000000000654061451257705100247340ustar00rootroot00000000000000#Sat Sep 05 17:45:34 CEST 2009 eclipse.preferences.version=1 org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.5 org.eclipse.jdt.core.compiler.compliance=1.5 org.eclipse.jdt.core.compiler.doc.comment.support=enabled org.eclipse.jdt.core.compiler.problem.annotationSuperInterface=warning org.eclipse.jdt.core.compiler.problem.assertIdentifier=error org.eclipse.jdt.core.compiler.problem.autoboxing=warning org.eclipse.jdt.core.compiler.problem.deprecation=warning org.eclipse.jdt.core.compiler.problem.deprecationInDeprecatedCode=disabled org.eclipse.jdt.core.compiler.problem.deprecationWhenOverridingDeprecatedMethod=disabled org.eclipse.jdt.core.compiler.problem.discouragedReference=warning org.eclipse.jdt.core.compiler.problem.emptyStatement=ignore org.eclipse.jdt.core.compiler.problem.enumIdentifier=error org.eclipse.jdt.core.compiler.problem.fallthroughCase=ignore org.eclipse.jdt.core.compiler.problem.fatalOptionalError=enabled org.eclipse.jdt.core.compiler.problem.fieldHiding=ignore org.eclipse.jdt.core.compiler.problem.finalParameterBound=warning org.eclipse.jdt.core.compiler.problem.finallyBlockNotCompletingNormally=warning org.eclipse.jdt.core.compiler.problem.forbiddenReference=error org.eclipse.jdt.core.compiler.problem.hiddenCatchBlock=warning org.eclipse.jdt.core.compiler.problem.incompatibleNonInheritedInterfaceMethod=warning org.eclipse.jdt.core.compiler.problem.incompleteEnumSwitch=ignore org.eclipse.jdt.core.compiler.problem.indirectStaticAccess=ignore org.eclipse.jdt.core.compiler.problem.invalidJavadoc=warning org.eclipse.jdt.core.compiler.problem.invalidJavadocTags=enabled org.eclipse.jdt.core.compiler.problem.invalidJavadocTagsDeprecatedRef=disabled org.eclipse.jdt.core.compiler.problem.invalidJavadocTagsNotVisibleRef=enabled org.eclipse.jdt.core.compiler.problem.invalidJavadocTagsVisibility=public org.eclipse.jdt.core.compiler.problem.localVariableHiding=ignore org.eclipse.jdt.core.compiler.problem.methodWithConstructorName=warning org.eclipse.jdt.core.compiler.problem.missingDeprecatedAnnotation=ignore org.eclipse.jdt.core.compiler.problem.missingJavadocComments=warning org.eclipse.jdt.core.compiler.problem.missingJavadocCommentsOverriding=disabled org.eclipse.jdt.core.compiler.problem.missingJavadocCommentsVisibility=protected org.eclipse.jdt.core.compiler.problem.missingJavadocTagDescription=no_tag org.eclipse.jdt.core.compiler.problem.missingJavadocTags=warning org.eclipse.jdt.core.compiler.problem.missingJavadocTagsOverriding=disabled org.eclipse.jdt.core.compiler.problem.missingJavadocTagsVisibility=protected org.eclipse.jdt.core.compiler.problem.missingOverrideAnnotation=error org.eclipse.jdt.core.compiler.problem.missingSerialVersion=warning org.eclipse.jdt.core.compiler.problem.noEffectAssignment=warning org.eclipse.jdt.core.compiler.problem.noImplicitStringConversion=warning org.eclipse.jdt.core.compiler.problem.nonExternalizedStringLiteral=ignore org.eclipse.jdt.core.compiler.problem.nullReference=warning org.eclipse.jdt.core.compiler.problem.overridingPackageDefaultMethod=warning org.eclipse.jdt.core.compiler.problem.parameterAssignment=ignore org.eclipse.jdt.core.compiler.problem.possibleAccidentalBooleanAssignment=ignore org.eclipse.jdt.core.compiler.problem.potentialNullReference=ignore org.eclipse.jdt.core.compiler.problem.rawTypeReference=warning org.eclipse.jdt.core.compiler.problem.redundantNullCheck=ignore org.eclipse.jdt.core.compiler.problem.redundantSuperinterface=ignore org.eclipse.jdt.core.compiler.problem.specialParameterHidingField=disabled org.eclipse.jdt.core.compiler.problem.staticAccessReceiver=warning org.eclipse.jdt.core.compiler.problem.suppressWarnings=enabled org.eclipse.jdt.core.compiler.problem.syntheticAccessEmulation=ignore org.eclipse.jdt.core.compiler.problem.typeParameterHiding=warning org.eclipse.jdt.core.compiler.problem.uncheckedTypeOperation=warning org.eclipse.jdt.core.compiler.problem.undocumentedEmptyBlock=ignore org.eclipse.jdt.core.compiler.problem.unhandledWarningToken=warning org.eclipse.jdt.core.compiler.problem.unnecessaryElse=ignore org.eclipse.jdt.core.compiler.problem.unnecessaryTypeCheck=ignore org.eclipse.jdt.core.compiler.problem.unqualifiedFieldAccess=ignore org.eclipse.jdt.core.compiler.problem.unusedDeclaredThrownException=ignore org.eclipse.jdt.core.compiler.problem.unusedDeclaredThrownExceptionExemptExceptionAndThrowable=enabled org.eclipse.jdt.core.compiler.problem.unusedDeclaredThrownExceptionIncludeDocCommentReference=enabled org.eclipse.jdt.core.compiler.problem.unusedDeclaredThrownExceptionWhenOverriding=disabled org.eclipse.jdt.core.compiler.problem.unusedImport=warning org.eclipse.jdt.core.compiler.problem.unusedLabel=warning org.eclipse.jdt.core.compiler.problem.unusedLocal=warning org.eclipse.jdt.core.compiler.problem.unusedParameter=warning org.eclipse.jdt.core.compiler.problem.unusedParameterIncludeDocCommentReference=disabled org.eclipse.jdt.core.compiler.problem.unusedParameterWhenImplementingAbstract=disabled org.eclipse.jdt.core.compiler.problem.unusedParameterWhenOverridingConcrete=disabled org.eclipse.jdt.core.compiler.problem.unusedPrivateMember=warning org.eclipse.jdt.core.compiler.problem.unusedWarningToken=warning org.eclipse.jdt.core.compiler.problem.varargsArgumentNeedCast=warning org.eclipse.jdt.core.compiler.source=1.5 org.eclipse.jdt.core.formatter.align_type_members_on_columns=false org.eclipse.jdt.core.formatter.alignment_for_arguments_in_allocation_expression=16 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_enum_constant=16 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_explicit_constructor_call=16 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_method_invocation=16 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_qualified_allocation_expression=16 org.eclipse.jdt.core.formatter.alignment_for_assignment=0 org.eclipse.jdt.core.formatter.alignment_for_binary_expression=16 org.eclipse.jdt.core.formatter.alignment_for_compact_if=16 org.eclipse.jdt.core.formatter.alignment_for_conditional_expression=80 org.eclipse.jdt.core.formatter.alignment_for_enum_constants=0 org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer=16 org.eclipse.jdt.core.formatter.alignment_for_multiple_fields=16 org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_parameters_in_method_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_selector_in_method_invocation=16 org.eclipse.jdt.core.formatter.alignment_for_superclass_in_type_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_enum_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_type_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_constructor_declaration=16 org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_method_declaration=16 org.eclipse.jdt.core.formatter.blank_lines_after_imports=1 org.eclipse.jdt.core.formatter.blank_lines_after_package=1 org.eclipse.jdt.core.formatter.blank_lines_before_field=0 org.eclipse.jdt.core.formatter.blank_lines_before_first_class_body_declaration=0 org.eclipse.jdt.core.formatter.blank_lines_before_imports=1 org.eclipse.jdt.core.formatter.blank_lines_before_member_type=1 org.eclipse.jdt.core.formatter.blank_lines_before_method=1 org.eclipse.jdt.core.formatter.blank_lines_before_new_chunk=1 org.eclipse.jdt.core.formatter.blank_lines_before_package=0 org.eclipse.jdt.core.formatter.blank_lines_between_import_groups=1 org.eclipse.jdt.core.formatter.blank_lines_between_type_declarations=1 org.eclipse.jdt.core.formatter.brace_position_for_annotation_type_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_anonymous_type_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_array_initializer=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_block=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_block_in_case=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_constructor_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_enum_constant=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_enum_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_method_declaration=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_switch=end_of_line org.eclipse.jdt.core.formatter.brace_position_for_type_declaration=end_of_line org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_block_comment=false org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_javadoc_comment=false org.eclipse.jdt.core.formatter.comment.format_block_comments=true org.eclipse.jdt.core.formatter.comment.format_header=false org.eclipse.jdt.core.formatter.comment.format_html=true org.eclipse.jdt.core.formatter.comment.format_javadoc_comments=true org.eclipse.jdt.core.formatter.comment.format_line_comments=true org.eclipse.jdt.core.formatter.comment.format_source_code=true org.eclipse.jdt.core.formatter.comment.indent_parameter_description=true org.eclipse.jdt.core.formatter.comment.indent_root_tags=true org.eclipse.jdt.core.formatter.comment.insert_new_line_before_root_tags=insert org.eclipse.jdt.core.formatter.comment.insert_new_line_for_parameter=insert org.eclipse.jdt.core.formatter.comment.line_length=80 org.eclipse.jdt.core.formatter.compact_else_if=true org.eclipse.jdt.core.formatter.continuation_indentation=2 org.eclipse.jdt.core.formatter.continuation_indentation_for_array_initializer=2 org.eclipse.jdt.core.formatter.format_guardian_clause_on_one_line=false org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_annotation_declaration_header=true org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_constant_header=true org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_declaration_header=true org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_type_header=true org.eclipse.jdt.core.formatter.indent_breaks_compare_to_cases=true org.eclipse.jdt.core.formatter.indent_empty_lines=false org.eclipse.jdt.core.formatter.indent_statements_compare_to_block=true org.eclipse.jdt.core.formatter.indent_statements_compare_to_body=true org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_cases=true org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_switch=false org.eclipse.jdt.core.formatter.indentation.size=4 org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_local_variable=insert org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_member=insert org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_parameter=do not insert org.eclipse.jdt.core.formatter.insert_new_line_after_opening_brace_in_array_initializer=do not insert org.eclipse.jdt.core.formatter.insert_new_line_at_end_of_file_if_missing=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_catch_in_try_statement=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_closing_brace_in_array_initializer=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_else_in_if_statement=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_finally_in_try_statement=do not insert org.eclipse.jdt.core.formatter.insert_new_line_before_while_in_do_statement=do not insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_annotation_declaration=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_anonymous_type_declaration=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_block=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_constant=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_declaration=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_method_body=insert org.eclipse.jdt.core.formatter.insert_new_line_in_empty_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_after_and_in_type_parameter=insert org.eclipse.jdt.core.formatter.insert_space_after_assignment_operator=insert org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation_type_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_after_binary_operator=insert org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_parameters=insert org.eclipse.jdt.core.formatter.insert_space_after_closing_brace_in_block=insert org.eclipse.jdt.core.formatter.insert_space_after_closing_paren_in_cast=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_assert=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_case=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_conditional=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_for=insert org.eclipse.jdt.core.formatter.insert_space_after_colon_in_labeled_statement=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_allocation_expression=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_annotation=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_array_initializer=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_parameters=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_throws=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_constant_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_declarations=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_explicitconstructorcall_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_increments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_inits=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_parameters=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_throws=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_invocation_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_field_declarations=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_local_declarations=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_parameterized_type_reference=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_superinterfaces=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_arguments=insert org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_parameters=insert org.eclipse.jdt.core.formatter.insert_space_after_ellipsis=insert org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_parameterized_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_brace_in_array_initializer=insert org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_cast=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_catch=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_constructor_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_enum_constant=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_for=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_if=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_invocation=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_parenthesized_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_switch=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_synchronized=do not insert org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_while=do not insert org.eclipse.jdt.core.formatter.insert_space_after_postfix_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_after_prefix_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_after_question_in_conditional=insert org.eclipse.jdt.core.formatter.insert_space_after_question_in_wildcard=do not insert org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_for=insert org.eclipse.jdt.core.formatter.insert_space_after_unary_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_before_and_in_type_parameter=insert org.eclipse.jdt.core.formatter.insert_space_before_assignment_operator=insert org.eclipse.jdt.core.formatter.insert_space_before_at_in_annotation_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_binary_operator=insert org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_parameterized_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_brace_in_array_initializer=insert org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_cast=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_catch=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_constructor_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_enum_constant=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_for=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_if=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_invocation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_parenthesized_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_switch=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_synchronized=do not insert org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_while=do not insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_assert=insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_case=do not insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_conditional=insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_default=do not insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_for=insert org.eclipse.jdt.core.formatter.insert_space_before_colon_in_labeled_statement=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_array_initializer=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_throws=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_constant_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_declarations=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_explicitconstructorcall_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_increments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_inits=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_throws=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_invocation_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_field_declarations=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_local_declarations=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_parameterized_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_superinterfaces=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_ellipsis=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_parameterized_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_arguments=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_parameters=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_annotation_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_anonymous_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_array_initializer=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_block=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_constructor_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_constant=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_method_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_switch=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_type_declaration=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation_type_member_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_catch=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_constructor_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_enum_constant=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_for=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_if=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_invocation=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_parenthesized_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_switch=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_synchronized=insert org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_while=insert org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_return=insert org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_throw=insert org.eclipse.jdt.core.formatter.insert_space_before_postfix_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_before_prefix_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_before_question_in_conditional=insert org.eclipse.jdt.core.formatter.insert_space_before_question_in_wildcard=do not insert org.eclipse.jdt.core.formatter.insert_space_before_semicolon=do not insert org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_for=do not insert org.eclipse.jdt.core.formatter.insert_space_before_unary_operator=do not insert org.eclipse.jdt.core.formatter.insert_space_between_brackets_in_array_type_reference=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_braces_in_array_initializer=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_brackets_in_array_allocation_expression=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_annotation_type_member_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_constructor_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_enum_constant=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_declaration=do not insert org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_invocation=do not insert org.eclipse.jdt.core.formatter.keep_else_statement_on_same_line=false org.eclipse.jdt.core.formatter.keep_empty_array_initializer_on_one_line=false org.eclipse.jdt.core.formatter.keep_imple_if_on_one_line=false org.eclipse.jdt.core.formatter.keep_then_statement_on_same_line=false org.eclipse.jdt.core.formatter.lineSplit=80 org.eclipse.jdt.core.formatter.never_indent_block_comments_on_first_column=false org.eclipse.jdt.core.formatter.never_indent_line_comments_on_first_column=false org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_method_body=0 org.eclipse.jdt.core.formatter.number_of_empty_lines_to_preserve=1 org.eclipse.jdt.core.formatter.put_empty_statement_on_new_line=true org.eclipse.jdt.core.formatter.tabulation.char=tab org.eclipse.jdt.core.formatter.tabulation.size=4 org.eclipse.jdt.core.formatter.use_tabs_only_for_leading_indentations=false org.eclipse.jdt.core.formatter.wrap_before_binary_operator=true jacoco-0.8.11/org.jacoco.core/.settings/org.eclipse.jdt.ui.prefs000066400000000000000000000063461451257705100244170ustar00rootroot00000000000000eclipse.preferences.version=1 editor_save_participant_org.eclipse.jdt.ui.postsavelistener.cleanup=true formatter_profile=org.eclipse.jdt.ui.default.eclipse_profile formatter_settings_version=11 org.eclipse.jdt.ui.text.custom_code_templates= sp_cleanup.add_default_serial_version_id=true sp_cleanup.add_generated_serial_version_id=false sp_cleanup.add_missing_annotations=true sp_cleanup.add_missing_deprecated_annotations=true sp_cleanup.add_missing_methods=false sp_cleanup.add_missing_nls_tags=false sp_cleanup.add_missing_override_annotations=true sp_cleanup.add_missing_override_annotations_interface_methods=false sp_cleanup.add_serial_version_id=false sp_cleanup.always_use_blocks=true sp_cleanup.always_use_parentheses_in_expressions=false sp_cleanup.always_use_this_for_non_static_field_access=false sp_cleanup.always_use_this_for_non_static_method_access=false sp_cleanup.convert_functional_interfaces=false sp_cleanup.convert_to_enhanced_for_loop=false sp_cleanup.correct_indentation=false sp_cleanup.format_source_code=true sp_cleanup.format_source_code_changes_only=false sp_cleanup.insert_inferred_type_arguments=false sp_cleanup.make_local_variable_final=true sp_cleanup.make_parameters_final=true sp_cleanup.make_private_fields_final=true sp_cleanup.make_type_abstract_if_missing_method=false sp_cleanup.make_variable_declarations_final=true sp_cleanup.never_use_blocks=false sp_cleanup.never_use_parentheses_in_expressions=true sp_cleanup.on_save_use_additional_actions=true sp_cleanup.organize_imports=true sp_cleanup.qualify_static_field_accesses_with_declaring_class=false sp_cleanup.qualify_static_member_accesses_through_instances_with_declaring_class=true sp_cleanup.qualify_static_member_accesses_through_subtypes_with_declaring_class=true sp_cleanup.qualify_static_member_accesses_with_declaring_class=true sp_cleanup.qualify_static_method_accesses_with_declaring_class=false sp_cleanup.remove_private_constructors=true sp_cleanup.remove_redundant_modifiers=false sp_cleanup.remove_redundant_semicolons=false sp_cleanup.remove_redundant_type_arguments=false sp_cleanup.remove_trailing_whitespaces=true sp_cleanup.remove_trailing_whitespaces_all=true sp_cleanup.remove_trailing_whitespaces_ignore_empty=false sp_cleanup.remove_unnecessary_casts=true sp_cleanup.remove_unnecessary_nls_tags=false sp_cleanup.remove_unused_imports=false sp_cleanup.remove_unused_local_variables=false sp_cleanup.remove_unused_private_fields=true sp_cleanup.remove_unused_private_members=false sp_cleanup.remove_unused_private_methods=true sp_cleanup.remove_unused_private_types=true sp_cleanup.sort_members=false sp_cleanup.sort_members_all=false sp_cleanup.use_anonymous_class_creation=false sp_cleanup.use_autoboxing=false sp_cleanup.use_blocks=true sp_cleanup.use_blocks_only_for_return_and_throw=false sp_cleanup.use_lambda=false sp_cleanup.use_parentheses_in_expressions=false sp_cleanup.use_this_for_non_static_field_access=false sp_cleanup.use_this_for_non_static_field_access_only_if_necessary=true sp_cleanup.use_this_for_non_static_method_access=false sp_cleanup.use_this_for_non_static_method_access_only_if_necessary=true sp_cleanup.use_unboxing=false jacoco-0.8.11/org.jacoco.core/about.html000066400000000000000000000014771451257705100200320ustar00rootroot00000000000000 About

About This Content

${build.date}

License

All Content in this distribution is made available by Mountainminds GmbH & Co. KG, Munich. Unless otherwise indicated below, the Content is provided to you under the terms and conditions of the Eclipse Public License Version 2.0 ("EPL"). A copy of the EPL is available at https://www.eclipse.org/legal/epl-2.0/. For purposes of the EPL, "Program" will mean the Content.

jacoco-0.8.11/org.jacoco.core/pom.xml000066400000000000000000000040451451257705100173410ustar00rootroot00000000000000 4.0.0 org.jacoco org.jacoco.build 0.8.11 ../org.jacoco.build org.jacoco.core JaCoCo :: Core JaCoCo Core org.ow2.asm asm org.ow2.asm asm-commons org.ow2.asm asm-tree src org.apache.felix maven-bundle-plugin process-classes manifest org.apache.maven.plugins maven-jar-plugin ${project.build.outputDirectory}/META-INF/MANIFEST.MF jacoco-0.8.11/org.jacoco.core/src/000077500000000000000000000000001451257705100166105ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core/src/org/000077500000000000000000000000001451257705100173775ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core/src/org/jacoco/000077500000000000000000000000001451257705100206355ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/000077500000000000000000000000001451257705100215655ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/JaCoCo.java000066400000000000000000000027451451257705100235360ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core; import java.util.ResourceBundle; /** * Static Meta information about JaCoCo. */ public final class JaCoCo { /** Qualified version of JaCoCo core. */ public static final String VERSION; /** Commit ID of the source tree of JaCoCo core. */ public static final String COMMITID; /** * Shortened (7 digit) commit ID of the source tree of JaCoCo core. */ public static final String COMMITID_SHORT; /** Absolute URL of the current JaCoCo home page */ public static final String HOMEURL; /** Name of the runtime package of this build */ public static final String RUNTIMEPACKAGE; static { final ResourceBundle bundle = ResourceBundle .getBundle("org.jacoco.core.jacoco"); VERSION = bundle.getString("VERSION"); COMMITID = bundle.getString("COMMITID"); COMMITID_SHORT = COMMITID.substring(0, 7); HOMEURL = bundle.getString("HOMEURL"); RUNTIMEPACKAGE = bundle.getString("RUNTIMEPACKAGE"); } private JaCoCo() { } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/000077500000000000000000000000001451257705100234105ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/Analyzer.java000066400000000000000000000225011451257705100260400ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; import java.io.File; import java.io.FileInputStream; import java.io.IOException; import java.io.InputStream; import java.util.StringTokenizer; import java.util.zip.GZIPInputStream; import java.util.zip.ZipEntry; import java.util.zip.ZipInputStream; import org.jacoco.core.JaCoCo; import org.jacoco.core.data.ExecutionData; import org.jacoco.core.data.ExecutionDataStore; import org.jacoco.core.internal.ContentTypeDetector; import org.jacoco.core.internal.InputStreams; import org.jacoco.core.internal.Pack200Streams; import org.jacoco.core.internal.analysis.ClassAnalyzer; import org.jacoco.core.internal.analysis.ClassCoverageImpl; import org.jacoco.core.internal.analysis.StringPool; import org.jacoco.core.internal.data.CRC64; import org.jacoco.core.internal.flow.ClassProbesAdapter; import org.jacoco.core.internal.instr.InstrSupport; import org.objectweb.asm.ClassReader; import org.objectweb.asm.ClassVisitor; import org.objectweb.asm.Opcodes; /** * An {@link Analyzer} instance processes a set of Java class files and * calculates coverage data for them. For each class file the result is reported * to a given {@link ICoverageVisitor} instance. In addition the * {@link Analyzer} requires a {@link ExecutionDataStore} instance that holds * the execution data for the classes to analyze. The {@link Analyzer} offers * several methods to analyze classes from a variety of sources. */ public class Analyzer { private final ExecutionDataStore executionData; private final ICoverageVisitor coverageVisitor; private final StringPool stringPool; /** * Creates a new analyzer reporting to the given output. * * @param executionData * execution data * @param coverageVisitor * the output instance that will coverage data for every analyzed * class */ public Analyzer(final ExecutionDataStore executionData, final ICoverageVisitor coverageVisitor) { this.executionData = executionData; this.coverageVisitor = coverageVisitor; this.stringPool = new StringPool(); } /** * Creates an ASM class visitor for analysis. * * @param classid * id of the class calculated with {@link CRC64} * @param className * VM name of the class * @return ASM visitor to write class definition to */ private ClassVisitor createAnalyzingVisitor(final long classid, final String className) { final ExecutionData data = executionData.get(classid); final boolean[] probes; final boolean noMatch; if (data == null) { probes = null; noMatch = executionData.contains(className); } else { probes = data.getProbes(); noMatch = false; } final ClassCoverageImpl coverage = new ClassCoverageImpl(className, classid, noMatch); final ClassAnalyzer analyzer = new ClassAnalyzer(coverage, probes, stringPool) { @Override public void visitEnd() { super.visitEnd(); coverageVisitor.visitCoverage(coverage); } }; return new ClassProbesAdapter(analyzer, false); } private void analyzeClass(final byte[] source) { final long classId = CRC64.classId(source); final ClassReader reader = InstrSupport.classReaderFor(source); if ((reader.getAccess() & Opcodes.ACC_MODULE) != 0) { return; } if ((reader.getAccess() & Opcodes.ACC_SYNTHETIC) != 0) { return; } final ClassVisitor visitor = createAnalyzingVisitor(classId, reader.getClassName()); reader.accept(visitor, 0); } /** * Analyzes the class definition from a given in-memory buffer. * * @param buffer * class definitions * @param location * a location description used for exception messages * @throws IOException * if the class can't be analyzed */ public void analyzeClass(final byte[] buffer, final String location) throws IOException { try { analyzeClass(buffer); } catch (final RuntimeException cause) { throw analyzerError(location, cause); } } /** * Analyzes the class definition from a given input stream. The provided * {@link InputStream} is not closed by this method. * * @param input * stream to read class definition from * @param location * a location description used for exception messages * @throws IOException * if the stream can't be read or the class can't be analyzed */ public void analyzeClass(final InputStream input, final String location) throws IOException { final byte[] buffer; try { buffer = InputStreams.readFully(input); } catch (final IOException e) { throw analyzerError(location, e); } analyzeClass(buffer, location); } private IOException analyzerError(final String location, final Exception cause) { final IOException ex = new IOException( String.format("Error while analyzing %s with JaCoCo %s/%s.", location, JaCoCo.VERSION, JaCoCo.COMMITID_SHORT)); ex.initCause(cause); return ex; } /** * Analyzes all classes found in the given input stream. The input stream * may either represent a single class file, a ZIP archive, a Pack200 * archive or a gzip stream that is searched recursively for class files. * All other content types are ignored. The provided {@link InputStream} is * not closed by this method. * * @param input * input data * @param location * a location description used for exception messages * @return number of class files found * @throws IOException * if the stream can't be read or a class can't be analyzed */ public int analyzeAll(final InputStream input, final String location) throws IOException { final ContentTypeDetector detector; try { detector = new ContentTypeDetector(input); } catch (final IOException e) { throw analyzerError(location, e); } switch (detector.getType()) { case ContentTypeDetector.CLASSFILE: analyzeClass(detector.getInputStream(), location); return 1; case ContentTypeDetector.ZIPFILE: return analyzeZip(detector.getInputStream(), location); case ContentTypeDetector.GZFILE: return analyzeGzip(detector.getInputStream(), location); case ContentTypeDetector.PACK200FILE: return analyzePack200(detector.getInputStream(), location); default: return 0; } } /** * Analyzes all class files contained in the given file or folder. Class * files as well as ZIP files are considered. Folders are searched * recursively. * * @param file * file or folder to look for class files * @return number of class files found * @throws IOException * if the file can't be read or a class can't be analyzed */ public int analyzeAll(final File file) throws IOException { int count = 0; if (file.isDirectory()) { for (final File f : file.listFiles()) { count += analyzeAll(f); } } else { final InputStream in = new FileInputStream(file); try { count += analyzeAll(in, file.getPath()); } finally { in.close(); } } return count; } /** * Analyzes all classes from the given class path. Directories containing * class files as well as archive files are considered. * * @param path * path definition * @param basedir * optional base directory, if null the current * working directory is used as the base for relative path * entries * @return number of class files found * @throws IOException * if a file can't be read or a class can't be analyzed */ public int analyzeAll(final String path, final File basedir) throws IOException { int count = 0; final StringTokenizer st = new StringTokenizer(path, File.pathSeparator); while (st.hasMoreTokens()) { count += analyzeAll(new File(basedir, st.nextToken())); } return count; } private int analyzeZip(final InputStream input, final String location) throws IOException { final ZipInputStream zip = new ZipInputStream(input); ZipEntry entry; int count = 0; while ((entry = nextEntry(zip, location)) != null) { count += analyzeAll(zip, location + "@" + entry.getName()); } return count; } private ZipEntry nextEntry(final ZipInputStream input, final String location) throws IOException { try { return input.getNextEntry(); } catch (final IOException e) { throw analyzerError(location, e); } } private int analyzeGzip(final InputStream input, final String location) throws IOException { GZIPInputStream gzipInputStream; try { gzipInputStream = new GZIPInputStream(input); } catch (final IOException e) { throw analyzerError(location, e); } return analyzeAll(gzipInputStream, location); } private int analyzePack200(final InputStream input, final String location) throws IOException { InputStream unpackedInput; try { unpackedInput = Pack200Streams.unpack(input); } catch (final IOException e) { throw analyzerError(location, e); } return analyzeAll(unpackedInput, location); } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/CounterComparator.java000066400000000000000000000054231451257705100277260ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; import java.io.Serializable; import java.util.Comparator; import org.jacoco.core.analysis.ICounter.CounterValue; import org.jacoco.core.analysis.ICoverageNode.CounterEntity; /** * Collection of comparators to compare {@link ICounter} objects by different * criteria. */ public class CounterComparator implements Comparator, Serializable { private static final long serialVersionUID = -3777463066252746748L; /** * Compares the absolute number of total items. */ public static final CounterComparator TOTALITEMS = new CounterComparator( CounterValue.TOTALCOUNT); /** * Compares the absolute number of covered items. */ public static final CounterComparator COVEREDITEMS = new CounterComparator( CounterValue.COVEREDCOUNT); /** * Compares the absolute number of missed items. */ public static final CounterComparator MISSEDITEMS = new CounterComparator( CounterValue.MISSEDCOUNT); /** * Compares the ratio of covered items. */ public static final CounterComparator COVEREDRATIO = new CounterComparator( CounterValue.COVEREDRATIO); /** * Compares the ratio of missed items. */ public static final CounterComparator MISSEDRATIO = new CounterComparator( CounterValue.MISSEDRATIO); private final CounterValue value; private final boolean reverse; private CounterComparator(final CounterValue value) { this(value, false); } private CounterComparator(final CounterValue value, final boolean reverse) { this.value = value; this.reverse = reverse; } public int compare(final ICounter c1, final ICounter c2) { final int cmp = Double.compare(c1.getValue(value), c2.getValue(value)); return reverse ? -cmp : cmp; } /** * Creates a new version of this comparator that sorts in reverse order. * * @return reverse comparator */ public CounterComparator reverse() { return new CounterComparator(value, !reverse); } /** * Creates a new comparator for {@link ICoverageNode} counters of the given * entity based on this counter sorting criteria. * * @param entity * counter entity to sort on * @return comparator for {@link ICoverageNode} elements */ public NodeComparator on(final CounterEntity entity) { return new NodeComparator(this, entity); } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/CoverageBuilder.java000066400000000000000000000076101451257705100273210ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; import java.util.ArrayList; import java.util.Collection; import java.util.Collections; import java.util.HashMap; import java.util.Map; import org.jacoco.core.internal.analysis.BundleCoverageImpl; import org.jacoco.core.internal.analysis.SourceFileCoverageImpl; /** * Builder for hierarchical {@link ICoverageNode} structures from single * {@link IClassCoverage} nodes. The nodes are feed into the builder through its * {@link ICoverageVisitor} interface. Afterwards the aggregated data can be * obtained with {@link #getClasses()}, {@link #getSourceFiles()} or * {@link #getBundle(String)} in the following hierarchy: * *
 * {@link IBundleCoverage}
 * +-- {@link IPackageCoverage}*
 *     +-- {@link IClassCoverage}*
 *     +-- {@link ISourceFileCoverage}*
 * 
*/ public class CoverageBuilder implements ICoverageVisitor { private final Map classes; private final Map sourcefiles; /** * Create a new builder. * */ public CoverageBuilder() { this.classes = new HashMap(); this.sourcefiles = new HashMap(); } /** * Returns all class nodes currently contained in this builder. * * @return all class nodes */ public Collection getClasses() { return Collections.unmodifiableCollection(classes.values()); } /** * Returns all source file nodes currently contained in this builder. * * @return all source file nodes */ public Collection getSourceFiles() { return Collections.unmodifiableCollection(sourcefiles.values()); } /** * Creates a bundle from all nodes currently contained in this bundle. * * @param name * Name of the bundle * @return bundle containing all classes and source files */ public IBundleCoverage getBundle(final String name) { return new BundleCoverageImpl(name, classes.values(), sourcefiles.values()); } /** * Returns all classes for which execution data does not match. * * @see IClassCoverage#isNoMatch() * @return collection of classes with non-matching execution data */ public Collection getNoMatchClasses() { final Collection result = new ArrayList(); for (final IClassCoverage c : classes.values()) { if (c.isNoMatch()) { result.add(c); } } return result; } // === ICoverageVisitor === public void visitCoverage(final IClassCoverage coverage) { final String name = coverage.getName(); final IClassCoverage dup = classes.put(name, coverage); if (dup != null) { if (dup.getId() != coverage.getId()) { throw new IllegalStateException( "Can't add different class with same name: " + name); } } else { final String source = coverage.getSourceFileName(); if (source != null) { final SourceFileCoverageImpl sourceFile = getSourceFile(source, coverage.getPackageName()); sourceFile.increment(coverage); } } } private SourceFileCoverageImpl getSourceFile(final String filename, final String packagename) { final String key = packagename + '/' + filename; SourceFileCoverageImpl sourcefile = (SourceFileCoverageImpl) sourcefiles .get(key); if (sourcefile == null) { sourcefile = new SourceFileCoverageImpl(filename, packagename); sourcefiles.put(key, sourcefile); } return sourcefile; } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/CoverageNodeImpl.java000066400000000000000000000107621451257705100274440ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; import java.util.Collection; import org.jacoco.core.internal.analysis.CounterImpl; /** * Base implementation for coverage data nodes. */ public class CoverageNodeImpl implements ICoverageNode { private final ElementType elementType; private final String name; /** Counter for branches. */ protected CounterImpl branchCounter; /** Counter for instructions. */ protected CounterImpl instructionCounter; /** Counter for lines */ protected CounterImpl lineCounter; /** Counter for complexity. */ protected CounterImpl complexityCounter; /** Counter for methods. */ protected CounterImpl methodCounter; /** Counter for classes. */ protected CounterImpl classCounter; /** * Creates a new coverage data node. * * @param elementType * type of the element represented by this instance * @param name * name of this node */ public CoverageNodeImpl(final ElementType elementType, final String name) { this.elementType = elementType; this.name = name; this.branchCounter = CounterImpl.COUNTER_0_0; this.instructionCounter = CounterImpl.COUNTER_0_0; this.complexityCounter = CounterImpl.COUNTER_0_0; this.methodCounter = CounterImpl.COUNTER_0_0; this.classCounter = CounterImpl.COUNTER_0_0; this.lineCounter = CounterImpl.COUNTER_0_0; } /** * Increments the counters by the values given by another element. * * @param child * counters to add */ public void increment(final ICoverageNode child) { instructionCounter = instructionCounter .increment(child.getInstructionCounter()); branchCounter = branchCounter.increment(child.getBranchCounter()); lineCounter = lineCounter.increment(child.getLineCounter()); complexityCounter = complexityCounter .increment(child.getComplexityCounter()); methodCounter = methodCounter.increment(child.getMethodCounter()); classCounter = classCounter.increment(child.getClassCounter()); } /** * Increments the counters by the values given by the collection of * elements. * * @param children * list of nodes, which counters will be added to this node */ public void increment(final Collection children) { for (final ICoverageNode child : children) { increment(child); } } // === ICoverageDataNode === public ElementType getElementType() { return elementType; } public String getName() { return name; } public ICounter getInstructionCounter() { return instructionCounter; } public ICounter getBranchCounter() { return branchCounter; } public ICounter getLineCounter() { return lineCounter; } public ICounter getComplexityCounter() { return complexityCounter; } public ICounter getMethodCounter() { return methodCounter; } public ICounter getClassCounter() { return classCounter; } public ICounter getCounter(final CounterEntity entity) { switch (entity) { case INSTRUCTION: return getInstructionCounter(); case BRANCH: return getBranchCounter(); case LINE: return getLineCounter(); case COMPLEXITY: return getComplexityCounter(); case METHOD: return getMethodCounter(); case CLASS: return getClassCounter(); } throw new AssertionError(entity); } public boolean containsCode() { return getInstructionCounter().getTotalCount() != 0; } public ICoverageNode getPlainCopy() { final CoverageNodeImpl copy = new CoverageNodeImpl(elementType, name); copy.instructionCounter = CounterImpl.getInstance(instructionCounter); copy.branchCounter = CounterImpl.getInstance(branchCounter); copy.lineCounter = CounterImpl.getInstance(lineCounter); copy.complexityCounter = CounterImpl.getInstance(complexityCounter); copy.methodCounter = CounterImpl.getInstance(methodCounter); copy.classCounter = CounterImpl.getInstance(classCounter); return copy; } @Override public String toString() { final StringBuilder sb = new StringBuilder(); sb.append(name).append(" [").append(elementType).append("]"); return sb.toString(); } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/IBundleCoverage.java000066400000000000000000000016101451257705100272470ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; import java.util.Collection; /** * Coverage data of a bundle. A bundle groups a collection of packages. * * @see IPackageCoverage */ public interface IBundleCoverage extends ICoverageNode { /** * Returns all packages contained in this bundle. * * @return all packages */ Collection getPackages(); } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/IClassCoverage.java000066400000000000000000000043551451257705100271140ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; import java.util.Collection; /** * Coverage data of a single class containing methods. The name of this node is * the fully qualified class name in VM notation (slash separated). * * @see IMethodCoverage */ public interface IClassCoverage extends ISourceNode { /** * Returns the identifier for this class which is the CRC64 signature of the * class definition. * * @return class identifier */ long getId(); /** * Returns if the the analyzed class does match the execution data provided. * More precisely if execution data is available for a class with the same * qualified name but with a different class id. * * @return true if this class does not match to the provided * execution data. */ boolean isNoMatch(); /** * Returns the VM signature of the class. * * @return VM signature of the class (may be null) */ String getSignature(); /** * Returns the VM name of the superclass. * * @return VM name of the super class (may be null, i.e. * java/lang/Object) */ String getSuperName(); /** * Returns the VM names of implemented/extended interfaces. * * @return VM names of implemented/extended interfaces */ String[] getInterfaceNames(); /** * Returns the VM name of the package this class belongs to. * * @return VM name of the package */ String getPackageName(); /** * Returns the optional name of the corresponding source file. * * @return name of the corresponding source file */ String getSourceFileName(); /** * Returns the methods included in this class. * * @return methods of this class */ Collection getMethods(); } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/ICounter.java000066400000000000000000000051031451257705100260020ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; /** * A counter holds the missed and the covered number of particular items like * classes, methods, branches or instructions. */ public interface ICounter { /** * Different values provided by a counter. */ enum CounterValue { /** Total number of items */ TOTALCOUNT, /** Number of missed items */ MISSEDCOUNT, /** Number of covered items */ COVEREDCOUNT, /** Ratio of missed to total items */ MISSEDRATIO, /** Ratio of covered to total items */ COVEREDRATIO } /** * Status flag for no items (value is 0x00). */ int EMPTY = 0x00; /** * Status flag when all items are not covered (value is 0x01). */ int NOT_COVERED = 0x01; /** * Status flag when all items are covered (value is 0x02). */ int FULLY_COVERED = 0x02; /** * Status flag when items are partly covered (value is 0x03). */ int PARTLY_COVERED = NOT_COVERED | FULLY_COVERED; /** * Returns the counter value of the given type. * * @param value * value type to return * @return counter value */ double getValue(CounterValue value); /** * Returns the total count of items. * * @return total count of items */ int getTotalCount(); /** * Returns the count of covered items. * * @return count of covered items */ int getCoveredCount(); /** * Returns the count of missed items. * * @return count of missed items */ int getMissedCount(); /** * Calculates the ratio of covered to total count items. If total count * items is 0 this method returns NaN. * * @return ratio of covered to total count items */ double getCoveredRatio(); /** * Calculates the ratio of missed to total count items. If total count items * is 0 this method returns NaN. * * @return ratio of missed to total count items */ double getMissedRatio(); /** * Returns the coverage status of this counter. * * @see ICounter#EMPTY * @see ICounter#NOT_COVERED * @see ICounter#PARTLY_COVERED * @see ICounter#FULLY_COVERED * * @return status of this line */ int getStatus(); } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/ICoverageNode.java000066400000000000000000000060251451257705100267300ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; /** * Interface for hierarchical coverage data nodes with different coverage * counters. */ public interface ICoverageNode { /** * Type of a Java element represented by a {@link ICoverageNode} instance. */ enum ElementType { /** Method */ METHOD, /** Class */ CLASS, /** Source File */ SOURCEFILE, /** Java Package */ PACKAGE, /** Bundle of Packages */ BUNDLE, /** Logical Group of Bundles */ GROUP, } /** * Different counter types supported by JaCoCo. */ enum CounterEntity { /** Counter for instructions */ INSTRUCTION, /** Counter for branches */ BRANCH, /** Counter for source lines */ LINE, /** Counter for cyclomatic complexity */ COMPLEXITY, /** Counter for methods */ METHOD, /** Counter for classes */ CLASS } /** * Returns the type of element represented by this node. * * @return type of this node */ ElementType getElementType(); /** * Returns the name of this node. * * @return name of this node */ String getName(); /** * Returns the counter for byte code instructions. * * @return counter for instructions */ ICounter getInstructionCounter(); /** * Returns the counter for branches. * * @return counter for branches */ ICounter getBranchCounter(); /** * Returns the counter for lines. * * @return counter for lines */ ICounter getLineCounter(); /** * Returns the counter for cyclomatic complexity. * * @return counter for complexity */ ICounter getComplexityCounter(); /** * Returns the counter for methods. * * @return counter for methods */ ICounter getMethodCounter(); /** * Returns the counter for classes. * * @return counter for classes */ ICounter getClassCounter(); /** * Generic access to the the counters. * * @param entity * entity we're we want to have the counter for * @return counter for the given entity */ ICounter getCounter(CounterEntity entity); /** * Checks whether this node contains code relevant for code coverage. * * @return true if this node contains code relevant for code * coverage */ boolean containsCode(); /** * Creates a plain copy of this node. While {@link ICoverageNode} * implementations may contain heavy data structures, the copy returned by * this method is reduced to the counters only. This helps to save memory * while processing huge structures. * * @return copy with counters only */ ICoverageNode getPlainCopy(); } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/ICoverageVisitor.java000066400000000000000000000015751451257705100275070ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; /** * Interface for coverage data output as a stream of {@link IClassCoverage} * instances. */ public interface ICoverageVisitor { /** * For analyzed class coverage data is emitted to this method. * * @param coverage * coverage data for a class */ void visitCoverage(IClassCoverage coverage); } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/ILine.java000066400000000000000000000023521451257705100252550ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; /** * The instruction and branch coverage of a single source line is described by * this interface. */ public interface ILine { /** * Returns the instruction counter for this line. * * @return instruction counter */ ICounter getInstructionCounter(); /** * Returns the branches counter for this line. * * @return branches counter */ ICounter getBranchCounter(); /** * Returns the coverage status of this line, calculated from the * instructions counter and branch counter. * * @see ICounter#EMPTY * @see ICounter#NOT_COVERED * @see ICounter#PARTLY_COVERED * @see ICounter#FULLY_COVERED * * @return status of this line */ int getStatus(); } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/IMethodCoverage.java000066400000000000000000000017151451257705100272640ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; /** * Coverage data of a single method. The name of this node is the local method * name. */ public interface IMethodCoverage extends ISourceNode { /** * Returns the descriptor of the method. * * @return descriptor */ String getDesc(); /** * Returns the generic signature of the method if defined. * * @return generic signature or null */ String getSignature(); } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/IPackageCoverage.java000066400000000000000000000022631451257705100273760ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; import java.util.Collection; /** * Coverage data of a Java package containing classes and source files. The name * of this node is the package name in VM notation (slash separated). The name * of the default package is the empty string. * * @see IClassCoverage * @see ISourceFileCoverage */ public interface IPackageCoverage extends ICoverageNode { /** * Returns all classes contained in this package. * * @return all classes */ Collection getClasses(); /** * Returns all source files in this package. * * @return all source files */ Collection getSourceFiles(); } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/ISourceFileCoverage.java000066400000000000000000000015561451257705100301070ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; /** * Coverage data of a single source file. The name of this node is the local * name of the source file. */ public interface ISourceFileCoverage extends ISourceNode { /** * Returns the VM name of the package the source file belongs to. * * @return package name */ String getPackageName(); } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/ISourceNode.java000066400000000000000000000026411451257705100264350ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; /** * Interface for coverage nodes that have individual source lines like methods, * classes and source files. */ public interface ISourceNode extends ICoverageNode { /** Place holder for unknown lines (no debug information) */ int UNKNOWN_LINE = -1; /** * The number of the first line coverage information is available for. If no * line is contained, the method returns -1. * * @return number of the first line or {@link #UNKNOWN_LINE} */ int getFirstLine(); /** * The number of the last line coverage information is available for. If no * line is contained, the method returns -1. * * @return number of the last line or {@link #UNKNOWN_LINE} */ int getLastLine(); /** * Returns the line information for given line. * * @param nr * line number of interest * @return line information */ ILine getLine(int nr); } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/NodeComparator.java000066400000000000000000000051311451257705100271700ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.analysis; import java.io.Serializable; import java.util.ArrayList; import java.util.Collection; import java.util.Collections; import java.util.Comparator; import java.util.List; import org.jacoco.core.analysis.ICoverageNode.CounterEntity; /** * Comparator to compare {@link ICoverageNode} objects by different counter * criteria. * * @see CounterComparator#on(ICoverageNode.CounterEntity) */ public class NodeComparator implements Comparator, Serializable { private static final long serialVersionUID = 8550521643608826519L; private final Comparator counterComparator; private final CounterEntity entity; NodeComparator(final Comparator counterComparator, final CounterEntity entity) { this.counterComparator = counterComparator; this.entity = entity; } /** * Creates a new composite comparator with a second search criterion. * * @param second * second criterion comparator * * @return composite comparator */ public NodeComparator second(final Comparator second) { final Comparator first = this; return new NodeComparator(null, null) { private static final long serialVersionUID = -5515272752138802838L; @Override public int compare(final ICoverageNode o1, final ICoverageNode o2) { final int result = first.compare(o1, o2); return result == 0 ? second.compare(o1, o2) : result; } }; } /** * Returns a sorted copy of the given collection of {@link ICoverageNode} * elements. * * @param * actual type of the elements * @param summaries * collection to create a copy of * @return sorted copy */ public List sort( final Collection summaries) { final List result = new ArrayList(summaries); Collections.sort(result, this); return result; } public int compare(final ICoverageNode n1, final ICoverageNode n2) { final ICounter c1 = n1.getCounter(entity); final ICounter c2 = n2.getCounter(entity); return counterComparator.compare(c1, c2); } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/analysis/package-info.java000066400000000000000000000032501451257705100265770ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ /** *

* Coverage calculation and analysis. The coverage information is calculated * with an {@link org.jacoco.core.analysis.Analyzer} instance from class files * (target) and {@linkplain org.jacoco.core.data.IExecutionDataVisitor execution * data} (actual). *

* *

* The {@link org.jacoco.core.analysis.CoverageBuilder} creates a hierarchy of * {@link org.jacoco.core.analysis.ICoverageNode} instances with the following * {@link org.jacoco.core.analysis.ICoverageNode.ElementType types}: *

* *
 * +-- {@linkplain org.jacoco.core.analysis.ICoverageNode.ElementType#GROUP Group} (optional)
 *     +-- {@linkplain org.jacoco.core.analysis.ICoverageNode.ElementType#BUNDLE Bundle}
 *         +-- {@linkplain org.jacoco.core.analysis.ICoverageNode.ElementType#PACKAGE Package}
 *             +-- {@linkplain org.jacoco.core.analysis.ICoverageNode.ElementType#SOURCEFILE Source File}
 *                 +-- {@linkplain org.jacoco.core.analysis.ICoverageNode.ElementType#CLASS Class}
 *                     +-- {@linkplain org.jacoco.core.analysis.ICoverageNode.ElementType#METHOD Method}
 * 
*/ package org.jacoco.core.analysis; jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/data/000077500000000000000000000000001451257705100224765ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/data/ExecutionData.java000066400000000000000000000122351451257705100261010ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; import static java.lang.String.format; import java.util.Arrays; /** * Execution data for a single Java class. While instances are immutable care * has to be taken about the probe data array of type boolean[] * which can be modified. */ public final class ExecutionData { private final long id; private final String name; private final boolean[] probes; /** * Creates a new {@link ExecutionData} object with the given probe data. * * @param id * class identifier * @param name * VM name * @param probes * probe data */ public ExecutionData(final long id, final String name, final boolean[] probes) { this.id = id; this.name = name; this.probes = probes; } /** * Creates a new {@link ExecutionData} object with the given probe data * length. All probes are set to false. * * @param id * class identifier * @param name * VM name * @param probeCount * probe count */ public ExecutionData(final long id, final String name, final int probeCount) { this.id = id; this.name = name; this.probes = new boolean[probeCount]; } /** * Return the unique identifier for this class. The identifier is the CRC64 * checksum of the raw class file definition. * * @return class identifier */ public long getId() { return id; } /** * The VM name of the class. * * @return VM name */ public String getName() { return name; } /** * Returns the execution data probes. A value of true indicates * that the corresponding probe was executed. * * @return probe data */ public boolean[] getProbes() { return probes; } /** * Sets all probes to false. */ public void reset() { Arrays.fill(probes, false); } /** * Checks whether any probe has been hit. * * @return true, if at least one probe has been hit */ public boolean hasHits() { for (final boolean p : probes) { if (p) { return true; } } return false; } /** * Merges the given execution data into the probe data of this object. I.e. * a probe entry in this object is marked as executed (true) if * this probe or the corresponding other probe was executed. So the result * is * *
	 * A or B
	 * 
* * The probe array of the other object is not modified. * * @param other * execution data to merge */ public void merge(final ExecutionData other) { merge(other, true); } /** * Merges the given execution data into the probe data of this object. A * probe in this object is set to the value of flag if the * corresponding other probe was executed. For flag==true this * corresponds to * *
	 * A or B
	 * 
* * For flag==false this can be considered as a subtraction * *
	 * A and not B
	 * 
* * The probe array of the other object is not modified. * * @param other * execution data to merge * @param flag * merge mode */ public void merge(final ExecutionData other, final boolean flag) { assertCompatibility(other.getId(), other.getName(), other.getProbes().length); final boolean[] otherData = other.getProbes(); for (int i = 0; i < probes.length; i++) { if (otherData[i]) { probes[i] = flag; } } } /** * Asserts that this execution data object is compatible with the given * parameters. The purpose of this check is to detect a very unlikely class * id collision. * * @param id * other class id, must be the same * @param name * other name, must be equal to this name * @param probecount * probe data length, must be the same as for this data * @throws IllegalStateException * if the given parameters do not match this instance */ public void assertCompatibility(final long id, final String name, final int probecount) throws IllegalStateException { if (this.id != id) { throw new IllegalStateException( format("Different ids (%016x and %016x).", Long.valueOf(this.id), Long.valueOf(id))); } if (!this.name.equals(name)) { throw new IllegalStateException( format("Different class names %s and %s for id %016x.", this.name, name, Long.valueOf(id))); } if (this.probes.length != probecount) { throw new IllegalStateException(format( "Incompatible execution data for class %s with id %016x.", name, Long.valueOf(id))); } } @Override public String toString() { return String.format("ExecutionData[name=%s, id=%016x]", name, Long.valueOf(id)); } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/data/ExecutionDataReader.java000066400000000000000000000111021451257705100272140ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; import static java.lang.String.format; import java.io.IOException; import java.io.InputStream; import org.jacoco.core.internal.data.CompactDataInput; /** * Deserialization of execution data from binary streams. */ public class ExecutionDataReader { /** Underlying data input */ protected final CompactDataInput in; private ISessionInfoVisitor sessionInfoVisitor = null; private IExecutionDataVisitor executionDataVisitor = null; private boolean firstBlock = true; /** * Creates a new reader based on the given input stream input. Depending on * the nature of the underlying stream input should be buffered as most data * is read in single bytes. * * @param input * input stream to read execution data from */ public ExecutionDataReader(final InputStream input) { this.in = new CompactDataInput(input); } /** * Sets an listener for session information. * * @param visitor * visitor to retrieve session info events */ public void setSessionInfoVisitor(final ISessionInfoVisitor visitor) { this.sessionInfoVisitor = visitor; } /** * Sets an listener for execution data. * * @param visitor * visitor to retrieve execution data events */ public void setExecutionDataVisitor(final IExecutionDataVisitor visitor) { this.executionDataVisitor = visitor; } /** * Reads all data and reports it to the corresponding visitors. The stream * is read until its end or a command confirmation has been sent. * * @return true if additional data can be expected after a * command has been executed. false if the end of the * stream has been reached. * @throws IOException * might be thrown by the underlying input stream * @throws IncompatibleExecDataVersionException * incompatible data version from different JaCoCo release */ public boolean read() throws IOException, IncompatibleExecDataVersionException { byte type; do { int i = in.read(); if (i == -1) { return false; // EOF } type = (byte) i; if (firstBlock && type != ExecutionDataWriter.BLOCK_HEADER) { throw new IOException("Invalid execution data file."); } firstBlock = false; } while (readBlock(type)); return true; } /** * Reads a block of data identified by the given id. Subclasses may * overwrite this method to support additional block types. * * @param blocktype * block type * @return true if there are more blocks to read * @throws IOException * might be thrown by the underlying input stream */ protected boolean readBlock(final byte blocktype) throws IOException { switch (blocktype) { case ExecutionDataWriter.BLOCK_HEADER: readHeader(); return true; case ExecutionDataWriter.BLOCK_SESSIONINFO: readSessionInfo(); return true; case ExecutionDataWriter.BLOCK_EXECUTIONDATA: readExecutionData(); return true; default: throw new IOException( format("Unknown block type %x.", Byte.valueOf(blocktype))); } } private void readHeader() throws IOException { if (in.readChar() != ExecutionDataWriter.MAGIC_NUMBER) { throw new IOException("Invalid execution data file."); } final char version = in.readChar(); if (version != ExecutionDataWriter.FORMAT_VERSION) { throw new IncompatibleExecDataVersionException(version); } } private void readSessionInfo() throws IOException { if (sessionInfoVisitor == null) { throw new IOException("No session info visitor."); } final String id = in.readUTF(); final long start = in.readLong(); final long dump = in.readLong(); sessionInfoVisitor.visitSessionInfo(new SessionInfo(id, start, dump)); } private void readExecutionData() throws IOException { if (executionDataVisitor == null) { throw new IOException("No execution data visitor."); } final long id = in.readLong(); final String name = in.readUTF(); final boolean[] probes = in.readBooleanArray(); executionDataVisitor .visitClassExecution(new ExecutionData(id, name, probes)); } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/data/ExecutionDataStore.java000066400000000000000000000126021451257705100271140ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; import java.util.ArrayList; import java.util.Collection; import java.util.HashMap; import java.util.HashSet; import java.util.Map; import java.util.Set; /** * In-memory data store for execution data. The data can be added through its * {@link IExecutionDataVisitor} interface. If execution data is provided * multiple times for the same class the data is merged, i.e. a probe is marked * as executed if it is reported as executed at least once. This allows to merge * coverage date from multiple runs. A instance of this class is not thread * safe. */ public final class ExecutionDataStore implements IExecutionDataVisitor { private final Map entries = new HashMap(); private final Set names = new HashSet(); /** * Adds the given {@link ExecutionData} object into the store. If there is * already execution data with this same class id, this structure is merged * with the given one. * * @param data * execution data to add or merge * @throws IllegalStateException * if the given {@link ExecutionData} object is not compatible * to a corresponding one, that is already contained * @see ExecutionData#assertCompatibility(long, String, int) */ public void put(final ExecutionData data) throws IllegalStateException { final Long id = Long.valueOf(data.getId()); final ExecutionData entry = entries.get(id); if (entry == null) { entries.put(id, data); names.add(data.getName()); } else { entry.merge(data); } } /** * Subtracts the probes in the given {@link ExecutionData} object from the * store. I.e. for all set probes in the given data object the corresponding * probes in this store will be unset. If there is no execution data with id * of the given data object this operation will have no effect. * * @param data * execution data to subtract * @throws IllegalStateException * if the given {@link ExecutionData} object is not compatible * to a corresponding one, that is already contained * @see ExecutionData#assertCompatibility(long, String, int) */ public void subtract(final ExecutionData data) throws IllegalStateException { final Long id = Long.valueOf(data.getId()); final ExecutionData entry = entries.get(id); if (entry != null) { entry.merge(data, false); } } /** * Subtracts all probes in the given execution data store from this store. * * @param store * execution data store to subtract * @see #subtract(ExecutionData) */ public void subtract(final ExecutionDataStore store) { for (final ExecutionData data : store.getContents()) { subtract(data); } } /** * Returns the {@link ExecutionData} entry with the given id if it exists in * this store. * * @param id * class id * @return execution data or null */ public ExecutionData get(final long id) { return entries.get(Long.valueOf(id)); } /** * Checks whether execution data for classes with the given name are * contained in the store. * * @param name * VM name * @return true if at least one class with the name is * contained. */ public boolean contains(final String name) { return names.contains(name); } /** * Returns the coverage data for the class with the given identifier. If * there is no data available under the given id a new entry is created. * * @param id * class identifier * @param name * VM name of the class * @param probecount * probe data length * @return execution data */ public ExecutionData get(final Long id, final String name, final int probecount) { ExecutionData entry = entries.get(id); if (entry == null) { entry = new ExecutionData(id.longValue(), name, probecount); entries.put(id, entry); names.add(name); } else { entry.assertCompatibility(id.longValue(), name, probecount); } return entry; } /** * Resets all execution data probes, i.e. marks them as not executed. The * execution data objects itself are not removed. */ public void reset() { for (final ExecutionData executionData : this.entries.values()) { executionData.reset(); } } /** * Returns a collection that represents current contents of the store. * * @return current contents */ public Collection getContents() { return new ArrayList(entries.values()); } /** * Writes the content of the store to the given visitor interface. * * @param visitor * interface to write content to */ public void accept(final IExecutionDataVisitor visitor) { for (final ExecutionData data : getContents()) { visitor.visitClassExecution(data); } } // === IExecutionDataVisitor === public void visitClassExecution(final ExecutionData data) { put(data); } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/data/ExecutionDataWriter.java000066400000000000000000000073021451257705100272750ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.OutputStream; import org.jacoco.core.internal.data.CompactDataOutput; /** * Serialization of execution data into binary streams. */ public class ExecutionDataWriter implements ISessionInfoVisitor, IExecutionDataVisitor { /** * File format version, will be incremented for each incompatible change. */ public static final char FORMAT_VERSION; static { // Runtime initialize to ensure javac does not inline the value. FORMAT_VERSION = 0x1007; } /** Magic number in header for file format identification. */ public static final char MAGIC_NUMBER = 0xC0C0; /** Block identifier for file headers. */ public static final byte BLOCK_HEADER = 0x01; /** Block identifier for session information. */ public static final byte BLOCK_SESSIONINFO = 0x10; /** Block identifier for execution data of a single class. */ public static final byte BLOCK_EXECUTIONDATA = 0x11; /** Underlying data output */ protected final CompactDataOutput out; /** * Creates a new writer based on the given output stream. Depending on the * nature of the underlying stream output should be buffered as most data is * written in single bytes. * * @param output * binary stream to write execution data to * @throws IOException * if the header can't be written */ public ExecutionDataWriter(final OutputStream output) throws IOException { this.out = new CompactDataOutput(output); writeHeader(); } /** * Writes an file header to identify the stream and its protocol version. * * @throws IOException * if the header can't be written */ private void writeHeader() throws IOException { out.writeByte(BLOCK_HEADER); out.writeChar(MAGIC_NUMBER); out.writeChar(FORMAT_VERSION); } /** * Flushes the underlying stream. * * @throws IOException * if the underlying stream can't be flushed */ public void flush() throws IOException { out.flush(); } public void visitSessionInfo(final SessionInfo info) { try { out.writeByte(BLOCK_SESSIONINFO); out.writeUTF(info.getId()); out.writeLong(info.getStartTimeStamp()); out.writeLong(info.getDumpTimeStamp()); } catch (final IOException e) { throw new RuntimeException(e); } } public void visitClassExecution(final ExecutionData data) { if (data.hasHits()) { try { out.writeByte(BLOCK_EXECUTIONDATA); out.writeLong(data.getId()); out.writeUTF(data.getName()); out.writeBooleanArray(data.getProbes()); } catch (final IOException e) { throw new RuntimeException(e); } } } /** * Returns the first bytes of a file that represents a valid execution data * file. In any case every execution data file starts with the three bytes * 0x01 0xC0 0xC0. * * @return first bytes of a execution data file */ public static final byte[] getFileHeader() { final ByteArrayOutputStream buffer = new ByteArrayOutputStream(); try { new ExecutionDataWriter(buffer); } catch (final IOException e) { // Must not happen with ByteArrayOutputStream throw new AssertionError(e); } return buffer.toByteArray(); } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/data/IExecutionDataVisitor.java000066400000000000000000000016661451257705100276000ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; /** * Interface for data output of collected execution data. This interface is * meant to be implemented by parties that want to retrieve data from the * coverage runtime. */ public interface IExecutionDataVisitor { /** * Provides execution data for a class. * * @param data * execution data for a class */ void visitClassExecution(ExecutionData data); } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/data/ISessionInfoVisitor.java000066400000000000000000000020311451257705100272650ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; /** * Interface for data output of collected session information. This interface is * meant to be implemented by parties that want to retrieve data from the * coverage runtime. */ public interface ISessionInfoVisitor { /** * Provides session information for the subsequent execution data calls. In * case of merged sessions this method might be called multiple times. * * @param info * session information */ void visitSessionInfo(SessionInfo info); } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/data/IncompatibleExecDataVersionException.java000066400000000000000000000033571451257705100326030ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann, somechris - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; import java.io.IOException; /** * Signals that execution data in an incompatible version was tried to read. */ public class IncompatibleExecDataVersionException extends IOException { private static final long serialVersionUID = 1L; private final int actualVersion; /** * Creates a new exception to flag version mismatches in execution data. * * @param actualVersion * version found in the exec data */ public IncompatibleExecDataVersionException(final int actualVersion) { super(String.format("Cannot read execution data version 0x%x. " + "This version of JaCoCo uses execution data version 0x%x.", Integer.valueOf(actualVersion), Integer.valueOf(ExecutionDataWriter.FORMAT_VERSION))); this.actualVersion = actualVersion; } /** * Gets the version expected in the execution data which can be read by this * version of JaCoCo. * * @return expected version in execution data */ public int getExpectedVersion() { return ExecutionDataWriter.FORMAT_VERSION; } /** * Gets the actual version found in the execution data. * * @return actual version in execution data */ public int getActualVersion() { return actualVersion; } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/data/SessionInfo.java000066400000000000000000000040721451257705100256030ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; /** * Data object describing a session which was the source of execution data. * {@link SessionInfo} instances can be sorted by dump date through the * {@link Comparable} interface. */ public class SessionInfo implements Comparable { private final String id; private final long start; private final long dump; /** * Create a immutable session info with the given data. * * @param id * arbitrary session identifier, must not be null * @param start * the epoc based time stamp when execution data recording has * been started * @param dump * the epoc based time stamp when execution data was collected */ public SessionInfo(final String id, final long start, final long dump) { if (id == null) { throw new IllegalArgumentException(); } this.id = id; this.start = start; this.dump = dump; } /** * @return identifier for this session */ public String getId() { return id; } /** * @return the epoc based time stamp when execution data recording has been * started */ public long getStartTimeStamp() { return start; } /** * @return the epoc based time stamp when execution data was collected */ public long getDumpTimeStamp() { return dump; } public int compareTo(final SessionInfo other) { if (this.dump < other.dump) { return -1; } if (this.dump > other.dump) { return +1; } return 0; } @Override public String toString() { return "SessionInfo[" + id + "]"; } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/data/SessionInfoStore.java000066400000000000000000000054311451257705100266200ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.data; import static java.lang.Math.max; import static java.lang.Math.min; import java.util.ArrayList; import java.util.Collections; import java.util.List; /** * Container to collect and merge session {@link SessionInfo} objects. A * instance of this class is not thread safe. */ public class SessionInfoStore implements ISessionInfoVisitor { private final List infos = new ArrayList(); /** * Tests whether the store is empty. * * @return true if the store is empty */ public boolean isEmpty() { return infos.isEmpty(); } /** * Returns all {@link SessionInfo} objects currently contained in the store. * The info objects are ordered by its natural ordering (i.e. by the dump * time stamp). * * @return list of stored {@link SessionInfo} objects */ public List getInfos() { final List copy = new ArrayList(infos); Collections.sort(copy); return copy; } /** * Returns a new session info with the given id that contains a merged * version from all contained version. The start timestamp is the minimum of * all contained sessions, the dump timestamp the maximum of all contained * sessions. If no session is currently contained both timestamps are set to * 0. * * @param id * identifier for the merged session info * @return new {@link SessionInfo} object * */ public SessionInfo getMerged(final String id) { if (infos.isEmpty()) { return new SessionInfo(id, 0, 0); } long start = Long.MAX_VALUE; long dump = Long.MIN_VALUE; for (final SessionInfo i : infos) { start = min(start, i.getStartTimeStamp()); dump = max(dump, i.getDumpTimeStamp()); } return new SessionInfo(id, start, dump); } /** * Writes all contained {@link SessionInfo} objects into the given visitor. * The info objects are emitted in chronological order by dump timestamp. * * @param visitor * visitor to emit {@link SessionInfo} objects to */ public void accept(final ISessionInfoVisitor visitor) { for (final SessionInfo i : getInfos()) { visitor.visitSessionInfo(i); } } // === ISessionInfoVisitor === public void visitSessionInfo(final SessionInfo info) { infos.add(info); } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/data/package-info.java000066400000000000000000000012131451257705100256620ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ /** * Representation and persistence of execution data and session information. */ package org.jacoco.core.data; jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/instr/000077500000000000000000000000001451257705100227245ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/instr/Instrumenter.java000066400000000000000000000245071451257705100262760ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.instr; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.util.zip.CRC32; import java.util.zip.GZIPInputStream; import java.util.zip.GZIPOutputStream; import java.util.zip.ZipEntry; import java.util.zip.ZipInputStream; import java.util.zip.ZipOutputStream; import org.jacoco.core.JaCoCo; import org.jacoco.core.internal.ContentTypeDetector; import org.jacoco.core.internal.InputStreams; import org.jacoco.core.internal.Pack200Streams; import org.jacoco.core.internal.data.CRC64; import org.jacoco.core.internal.flow.ClassProbesAdapter; import org.jacoco.core.internal.instr.ClassInstrumenter; import org.jacoco.core.internal.instr.IProbeArrayStrategy; import org.jacoco.core.internal.instr.InstrSupport; import org.jacoco.core.internal.instr.ProbeArrayStrategyFactory; import org.jacoco.core.internal.instr.SignatureRemover; import org.jacoco.core.runtime.IExecutionDataAccessorGenerator; import org.objectweb.asm.ClassReader; import org.objectweb.asm.ClassVisitor; import org.objectweb.asm.ClassWriter; /** * Several APIs to instrument Java class definitions for coverage tracing. */ public class Instrumenter { private final IExecutionDataAccessorGenerator accessorGenerator; private final SignatureRemover signatureRemover; /** * Creates a new instance based on the given runtime. * * @param runtime * runtime used by the instrumented classes */ public Instrumenter(final IExecutionDataAccessorGenerator runtime) { this.accessorGenerator = runtime; this.signatureRemover = new SignatureRemover(); } /** * Determines whether signatures should be removed from JAR files. This is * typically necessary as instrumentation modifies the class files and * therefore invalidates existing JAR signatures. Default is * true. * * @param flag * true if signatures should be removed */ public void setRemoveSignatures(final boolean flag) { signatureRemover.setActive(flag); } private byte[] instrument(final byte[] source) { final long classId = CRC64.classId(source); final ClassReader reader = InstrSupport.classReaderFor(source); final ClassWriter writer = new ClassWriter(reader, 0) { @Override protected String getCommonSuperClass(final String type1, final String type2) { throw new IllegalStateException(); } }; final IProbeArrayStrategy strategy = ProbeArrayStrategyFactory .createFor(classId, reader, accessorGenerator); final int version = InstrSupport.getMajorVersion(reader); final ClassVisitor visitor = new ClassProbesAdapter( new ClassInstrumenter(strategy, writer), InstrSupport.needsFrames(version)); reader.accept(visitor, ClassReader.EXPAND_FRAMES); return writer.toByteArray(); } /** * Creates a instrumented version of the given class if possible. * * @param buffer * definition of the class * @param name * a name used for exception messages * @return instrumented definition * @throws IOException * if the class can't be instrumented */ public byte[] instrument(final byte[] buffer, final String name) throws IOException { try { return instrument(buffer); } catch (final RuntimeException e) { throw instrumentError(name, e); } } /** * Creates a instrumented version of the given class if possible. The * provided {@link InputStream} is not closed by this method. * * @param input * stream to read class definition from * @param name * a name used for exception messages * @return instrumented definition * @throws IOException * if reading data from the stream fails or the class can't be * instrumented */ public byte[] instrument(final InputStream input, final String name) throws IOException { final byte[] bytes; try { bytes = InputStreams.readFully(input); } catch (final IOException e) { throw instrumentError(name, e); } return instrument(bytes, name); } /** * Creates a instrumented version of the given class file. The provided * {@link InputStream} and {@link OutputStream} instances are not closed by * this method. * * @param input * stream to read class definition from * @param output * stream to write the instrumented version of the class to * @param name * a name used for exception messages * @throws IOException * if reading data from the stream fails or the class can't be * instrumented */ public void instrument(final InputStream input, final OutputStream output, final String name) throws IOException { output.write(instrument(input, name)); } private IOException instrumentError(final String name, final Exception cause) { final IOException ex = new IOException( String.format("Error while instrumenting %s with JaCoCo %s/%s.", name, JaCoCo.VERSION, JaCoCo.COMMITID_SHORT)); ex.initCause(cause); return ex; } /** * Creates a instrumented version of the given resource depending on its * type. Class files and the content of archive files are instrumented. All * other files are copied without modification. The provided * {@link InputStream} and {@link OutputStream} instances are not closed by * this method. * * @param input * stream to contents from * @param output * stream to write the instrumented version of the contents * @param name * a name used for exception messages * @return number of instrumented classes * @throws IOException * if reading data from the stream fails or a class can't be * instrumented */ public int instrumentAll(final InputStream input, final OutputStream output, final String name) throws IOException { final ContentTypeDetector detector; try { detector = new ContentTypeDetector(input); } catch (final IOException e) { throw instrumentError(name, e); } switch (detector.getType()) { case ContentTypeDetector.CLASSFILE: instrument(detector.getInputStream(), output, name); return 1; case ContentTypeDetector.ZIPFILE: return instrumentZip(detector.getInputStream(), output, name); case ContentTypeDetector.GZFILE: return instrumentGzip(detector.getInputStream(), output, name); case ContentTypeDetector.PACK200FILE: return instrumentPack200(detector.getInputStream(), output, name); default: copy(detector.getInputStream(), output, name); return 0; } } private int instrumentZip(final InputStream input, final OutputStream output, final String name) throws IOException { final ZipInputStream zipin = new ZipInputStream(input); final ZipOutputStream zipout = new ZipOutputStream(output); ZipEntry entry; int count = 0; while ((entry = nextEntry(zipin, name)) != null) { final String entryName = entry.getName(); if (signatureRemover.removeEntry(entryName)) { continue; } final ZipEntry newEntry = new ZipEntry(entryName); newEntry.setMethod(entry.getMethod()); switch (entry.getMethod()) { case ZipEntry.DEFLATED: zipout.putNextEntry(newEntry); count += filterOrInstrument(zipin, zipout, name, entryName); break; case ZipEntry.STORED: // Uncompressed entries must be processed in-memory to calculate // mandatory entry size and CRC final ByteArrayOutputStream buffer = new ByteArrayOutputStream(); count += filterOrInstrument(zipin, buffer, name, entryName); final byte[] bytes = buffer.toByteArray(); newEntry.setSize(bytes.length); newEntry.setCompressedSize(bytes.length); newEntry.setCrc(crc(bytes)); zipout.putNextEntry(newEntry); zipout.write(bytes); break; default: throw new AssertionError(entry.getMethod()); } zipout.closeEntry(); } zipout.finish(); return count; } private int filterOrInstrument(final InputStream in, final OutputStream out, final String name, final String entryName) throws IOException { if (signatureRemover.filterEntry(entryName, in, out)) { return 0; } else { return instrumentAll(in, out, name + "@" + entryName); } } private static long crc(final byte[] data) { final CRC32 crc = new CRC32(); crc.update(data); return crc.getValue(); } private ZipEntry nextEntry(final ZipInputStream input, final String location) throws IOException { try { return input.getNextEntry(); } catch (final IOException e) { throw instrumentError(location, e); } } private int instrumentGzip(final InputStream input, final OutputStream output, final String name) throws IOException { final GZIPInputStream gzipInputStream; try { gzipInputStream = new GZIPInputStream(input); } catch (final IOException e) { throw instrumentError(name, e); } final GZIPOutputStream gzout = new GZIPOutputStream(output); final int count = instrumentAll(gzipInputStream, gzout, name); gzout.finish(); return count; } private int instrumentPack200(final InputStream input, final OutputStream output, final String name) throws IOException { final InputStream unpackedInput; try { unpackedInput = Pack200Streams.unpack(input); } catch (final IOException e) { throw instrumentError(name, e); } final ByteArrayOutputStream buffer = new ByteArrayOutputStream(); final int count = instrumentAll(unpackedInput, buffer, name); Pack200Streams.pack(buffer.toByteArray(), output); return count; } private void copy(final InputStream input, final OutputStream output, final String name) throws IOException { final byte[] buffer = new byte[1024]; int len; while ((len = read(input, buffer, name)) != -1) { output.write(buffer, 0, len); } } private int read(final InputStream input, final byte[] buffer, final String name) throws IOException { try { return input.read(buffer); } catch (final IOException e) { throw instrumentError(name, e); } } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/instr/package-info.java000066400000000000000000000013311451257705100261110ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ /** *

* Instrumentation of Java class files for code coverage. The main entry point * is the class {@link org.jacoco.core.instr.Instrumenter}. *

*/ package org.jacoco.core.instr; jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/internal/000077500000000000000000000000001451257705100234015ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/internal/ContentTypeDetector.java000066400000000000000000000061621451257705100302170ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal; import java.io.BufferedInputStream; import java.io.IOException; import java.io.InputStream; /** * Detector for content types of binary streams based on a magic headers. */ public class ContentTypeDetector { /** Unknown file type */ public static final int UNKNOWN = -1; /** File type Java class */ public static final int CLASSFILE = 0xcafebabe; /** File type ZIP archive */ public static final int ZIPFILE = 0x504b0304; /** File type GZIP compressed Data */ public static final int GZFILE = 0x1f8b0000; /** File type Pack200 archive */ public static final int PACK200FILE = 0xcafed00d; private static final int BUFFER_SIZE = 8; private final InputStream in; private final int type; /** * Creates a new detector based on the given input. To process the complete * original input afterwards use the stream returned by * {@link #getInputStream()}. * * @param in * input to read the header from * @throws IOException * if the stream can't be read */ public ContentTypeDetector(final InputStream in) throws IOException { if (in.markSupported()) { this.in = in; } else { this.in = new BufferedInputStream(in, BUFFER_SIZE); } this.in.mark(BUFFER_SIZE); this.type = determineType(this.in); this.in.reset(); } private static int determineType(final InputStream in) throws IOException { final int header = readInt(in); switch (header) { case ZIPFILE: return ZIPFILE; case PACK200FILE: return PACK200FILE; case CLASSFILE: // Mach-O fat/universal binaries have the same magic header as Java // class files, number of architectures is stored in unsigned 4 // bytes in the same place and in the same big-endian order as major // and minor version of class file. Hopefully on practice number of // architectures in single executable is less than 45, which is // major version of Java 1.1 class files: final int majorVersion = readInt(in) & 0xFFFF; if (majorVersion >= 45) { return CLASSFILE; } } if ((header & 0xffff0000) == GZFILE) { return GZFILE; } return UNKNOWN; } private static int readInt(final InputStream in) throws IOException { return in.read() << 24 | in.read() << 16 | in.read() << 8 | in.read(); } /** * Returns an input stream instance to read the complete content (including * the header) of the underlying stream. * * @return input stream containing the complete content */ public InputStream getInputStream() { return in; } /** * Returns the detected file type. * * @return file type */ public int getType() { return type; } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/internal/InputStreams.java000066400000000000000000000026241451257705100267060ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Evgeny Mandrikov - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.InputStream; /** * Utilities for {@link InputStream}s. */ public final class InputStreams { private InputStreams() { } /** * Reads all bytes from an input stream into a byte array. The provided * {@link InputStream} is not closed by this method. * * @param is * the input stream to read from * @return a byte array containing all the bytes from the stream * @throws IOException * if an I/O error occurs */ public static byte[] readFully(final InputStream is) throws IOException { final byte[] buf = new byte[1024]; final ByteArrayOutputStream out = new ByteArrayOutputStream(); while (true) { final int r = is.read(buf); if (r == -1) { break; } out.write(buf, 0, r); } return out.toByteArray(); } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/internal/Pack200Streams.java000066400000000000000000000071141451257705100267060ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.FilterInputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.lang.reflect.InvocationTargetException; import java.util.jar.JarInputStream; import java.util.jar.JarOutputStream; /** * Internal wrapper for the weird Pack200 Java API to allow usage with streams. */ public final class Pack200Streams { /** * Unpack a stream in Pack200 format into a stream in JAR/ZIP format. * * @param input * stream in Pack200 format * @return stream in JAR/ZIP format * @throws IOException * in case of errors with the streams */ @SuppressWarnings("resource") public static InputStream unpack(final InputStream input) throws IOException { final ByteArrayOutputStream buffer = new ByteArrayOutputStream(); final JarOutputStream jar = new JarOutputStream(buffer); try { final Object unpacker = Class.forName("java.util.jar.Pack200") .getMethod("newUnpacker").invoke(null); Class.forName("java.util.jar.Pack200$Unpacker") .getMethod("unpack", InputStream.class, JarOutputStream.class) .invoke(unpacker, new NoCloseInput(input), jar); } catch (ClassNotFoundException e) { throw newIOException(e); } catch (NoSuchMethodException e) { throw newIOException(e); } catch (IllegalAccessException e) { throw newIOException(e); } catch (InvocationTargetException e) { throw newIOException(e.getCause()); } jar.finish(); return new ByteArrayInputStream(buffer.toByteArray()); } /** * Packs a buffer in JAR/ZIP format into a stream in Pack200 format. * * @param source * source in JAR/ZIP format * @param output * stream in Pack200 format * @throws IOException * in case of errors with the streams */ @SuppressWarnings("resource") public static void pack(final byte[] source, final OutputStream output) throws IOException { final JarInputStream jar = new JarInputStream( new ByteArrayInputStream(source)); try { final Object packer = Class.forName("java.util.jar.Pack200") .getMethod("newPacker").invoke(null); Class.forName("java.util.jar.Pack200$Packer") .getMethod("pack", JarInputStream.class, OutputStream.class) .invoke(packer, jar, output); } catch (ClassNotFoundException e) { throw newIOException(e); } catch (NoSuchMethodException e) { throw newIOException(e); } catch (IllegalAccessException e) { throw newIOException(e); } catch (InvocationTargetException e) { throw newIOException(e.getCause()); } } private static IOException newIOException(final Throwable cause) { final IOException exception = new IOException(); exception.initCause(cause); return exception; } private static class NoCloseInput extends FilterInputStream { protected NoCloseInput(final InputStream in) { super(in); } @Override public void close() throws IOException { // do not close the underlying stream } } private Pack200Streams() { } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/internal/analysis/000077500000000000000000000000001451257705100252245ustar00rootroot00000000000000jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/internal/analysis/BundleCoverageImpl.java000066400000000000000000000072611451257705100316040ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import java.util.ArrayList; import java.util.Collection; import java.util.Collections; import java.util.HashMap; import java.util.HashSet; import java.util.Map; import java.util.Set; import org.jacoco.core.analysis.CoverageNodeImpl; import org.jacoco.core.analysis.IBundleCoverage; import org.jacoco.core.analysis.IClassCoverage; import org.jacoco.core.analysis.IPackageCoverage; import org.jacoco.core.analysis.ISourceFileCoverage; /** * Implementation of {@link IBundleCoverage}. */ public class BundleCoverageImpl extends CoverageNodeImpl implements IBundleCoverage { private final Collection packages; /** * Creates a new instance of a bundle with the given name. * * @param name * name of this bundle * @param packages * collection of all packages contained in this bundle */ public BundleCoverageImpl(final String name, final Collection packages) { super(ElementType.BUNDLE, name); this.packages = packages; increment(packages); } /** * Creates a new instance of a bundle with the given name. The packages are * calculated from the given classes and source files. * * @param name * name of this bundle * @param classes * all classes in this bundle * @param sourcefiles * all source files in this bundle */ public BundleCoverageImpl(final String name, final Collection classes, final Collection sourcefiles) { this(name, groupByPackage(classes, sourcefiles)); } private static Collection groupByPackage( final Collection classes, final Collection sourcefiles) { final Map> classesByPackage = new HashMap>(); for (final IClassCoverage c : classes) { addByName(classesByPackage, c.getPackageName(), c); } final Map> sourceFilesByPackage = new HashMap>(); for (final ISourceFileCoverage s : sourcefiles) { addByName(sourceFilesByPackage, s.getPackageName(), s); } final Set packageNames = new HashSet(); packageNames.addAll(classesByPackage.keySet()); packageNames.addAll(sourceFilesByPackage.keySet()); final Collection result = new ArrayList(); for (final String name : packageNames) { Collection c = classesByPackage.get(name); if (c == null) { c = Collections.emptyList(); } Collection s = sourceFilesByPackage.get(name); if (s == null) { s = Collections.emptyList(); } result.add(new PackageCoverageImpl(name, c, s)); } return result; } private static void addByName(final Map> map, final String name, final T value) { Collection list = map.get(name); if (list == null) { list = new ArrayList(); map.put(name, list); } list.add(value); } // === IBundleCoverage implementation === public Collection getPackages() { return packages; } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/internal/analysis/ClassAnalyzer.java000066400000000000000000000116111451257705100306420ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import java.util.HashSet; import java.util.Set; import org.jacoco.core.internal.analysis.filter.Filters; import org.jacoco.core.internal.analysis.filter.IFilter; import org.jacoco.core.internal.analysis.filter.IFilterContext; import org.jacoco.core.internal.flow.ClassProbesVisitor; import org.jacoco.core.internal.flow.MethodProbesVisitor; import org.jacoco.core.internal.instr.InstrSupport; import org.objectweb.asm.AnnotationVisitor; import org.objectweb.asm.Attribute; import org.objectweb.asm.FieldVisitor; import org.objectweb.asm.MethodVisitor; import org.objectweb.asm.tree.MethodNode; /** * Analyzes the structure of a class. */ public class ClassAnalyzer extends ClassProbesVisitor implements IFilterContext { private final ClassCoverageImpl coverage; private final boolean[] probes; private final StringPool stringPool; private final Set classAnnotations = new HashSet(); private final Set classAttributes = new HashSet(); private String sourceDebugExtension; private final IFilter filter; /** * Creates a new analyzer that builds coverage data for a class. * * @param coverage * coverage node for the analyzed class data * @param probes * execution data for this class or null * @param stringPool * shared pool to minimize the number of {@link String} instances */ public ClassAnalyzer(final ClassCoverageImpl coverage, final boolean[] probes, final StringPool stringPool) { this.coverage = coverage; this.probes = probes; this.stringPool = stringPool; this.filter = Filters.all(); } @Override public void visit(final int version, final int access, final String name, final String signature, final String superName, final String[] interfaces) { coverage.setSignature(stringPool.get(signature)); coverage.setSuperName(stringPool.get(superName)); coverage.setInterfaces(stringPool.get(interfaces)); } @Override public AnnotationVisitor visitAnnotation(final String desc, final boolean visible) { classAnnotations.add(desc); return super.visitAnnotation(desc, visible); } @Override public void visitAttribute(final Attribute attribute) { classAttributes.add(attribute.type); } @Override public void visitSource(final String source, final String debug) { coverage.setSourceFileName(stringPool.get(source)); sourceDebugExtension = debug; } @Override public MethodProbesVisitor visitMethod(final int access, final String name, final String desc, final String signature, final String[] exceptions) { InstrSupport.assertNotInstrumented(name, coverage.getName()); final InstructionsBuilder builder = new InstructionsBuilder(probes); return new MethodAnalyzer(builder) { @Override public void accept(final MethodNode methodNode, final MethodVisitor methodVisitor) { super.accept(methodNode, methodVisitor); addMethodCoverage(stringPool.get(name), stringPool.get(desc), stringPool.get(signature), builder, methodNode); } }; } private void addMethodCoverage(final String name, final String desc, final String signature, final InstructionsBuilder icc, final MethodNode methodNode) { final MethodCoverageCalculator mcc = new MethodCoverageCalculator( icc.getInstructions()); filter.filter(methodNode, this, mcc); final MethodCoverageImpl mc = new MethodCoverageImpl(name, desc, signature); mcc.calculate(mc); if (mc.containsCode()) { // Only consider methods that actually contain code coverage.addMethod(mc); } } @Override public FieldVisitor visitField(final int access, final String name, final String desc, final String signature, final Object value) { InstrSupport.assertNotInstrumented(name, coverage.getName()); return super.visitField(access, name, desc, signature, value); } @Override public void visitTotalProbeCount(final int count) { // nothing to do } // IFilterContext implementation public String getClassName() { return coverage.getName(); } public String getSuperClassName() { return coverage.getSuperName(); } public Set getClassAnnotations() { return classAnnotations; } public Set getClassAttributes() { return classAttributes; } public String getSourceFileName() { return coverage.getSourceFileName(); } public String getSourceDebugExtension() { return sourceDebugExtension; } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/internal/analysis/ClassCoverageImpl.java000066400000000000000000000070751451257705100314430ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import java.util.ArrayList; import java.util.Collection; import org.jacoco.core.analysis.IClassCoverage; import org.jacoco.core.analysis.IMethodCoverage; /** * Implementation of {@link IClassCoverage}. */ public class ClassCoverageImpl extends SourceNodeImpl implements IClassCoverage { private final long id; private final boolean noMatch; private final Collection methods; private String signature; private String superName; private String[] interfaces; private String sourceFileName; /** * Creates a class coverage data object with the given parameters. * * @param name * VM name of the class * @param id * class identifier * @param noMatch * true, if class id does not match with execution * data */ public ClassCoverageImpl(final String name, final long id, final boolean noMatch) { super(ElementType.CLASS, name); this.id = id; this.noMatch = noMatch; this.methods = new ArrayList(); } /** * Add a method to this class. * * @param method * method data to add */ public void addMethod(final IMethodCoverage method) { this.methods.add(method); increment(method); // Class is considered as covered when at least one method is covered: if (methodCounter.getCoveredCount() > 0) { this.classCounter = CounterImpl.COUNTER_0_1; } else { this.classCounter = CounterImpl.COUNTER_1_0; } } /** * Sets the VM signature of the class. * * @param signature * VM signature of the class (may be null) */ public void setSignature(final String signature) { this.signature = signature; } /** * Sets the VM name of the superclass. * * @param superName * VM name of the super class (may be null, i.e. * java/lang/Object) */ public void setSuperName(final String superName) { this.superName = superName; } /** * Sets the VM names of implemented/extended interfaces. * * @param interfaces * VM names of implemented/extended interfaces */ public void setInterfaces(final String[] interfaces) { this.interfaces = interfaces; } /** * Sets the name of the corresponding source file for this class. * * @param sourceFileName * name of the source file */ public void setSourceFileName(final String sourceFileName) { this.sourceFileName = sourceFileName; } // === IClassCoverage implementation === public long getId() { return id; } public boolean isNoMatch() { return noMatch; } public String getSignature() { return signature; } public String getSuperName() { return superName; } public String[] getInterfaceNames() { return interfaces; } public String getPackageName() { final int pos = getName().lastIndexOf('/'); return pos == -1 ? "" : getName().substring(0, pos); } public String getSourceFileName() { return sourceFileName; } public Collection getMethods() { return methods; } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/internal/analysis/CounterImpl.java000066400000000000000000000131641451257705100303350ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import org.jacoco.core.analysis.ICounter; /** * {@link ICounter} implementations. Implementing a factory pattern allows to * share counter instances. */ public abstract class CounterImpl implements ICounter { /** Max counter value for which singletons are created */ private static final int SINGLETON_LIMIT = 30; private static final CounterImpl[][] SINGLETONS = new CounterImpl[SINGLETON_LIMIT + 1][]; static { for (int i = 0; i <= SINGLETON_LIMIT; i++) { SINGLETONS[i] = new CounterImpl[SINGLETON_LIMIT + 1]; for (int j = 0; j <= SINGLETON_LIMIT; j++) { SINGLETONS[i][j] = new Fix(i, j); } } } /** Constant for Counter with 0/0 values. */ public static final CounterImpl COUNTER_0_0 = SINGLETONS[0][0]; /** Constant for Counter with 1/0 values. */ public static final CounterImpl COUNTER_1_0 = SINGLETONS[1][0]; /** Constant for Counter with 0/1 values. */ public static final CounterImpl COUNTER_0_1 = SINGLETONS[0][1]; /** * Mutable version of the counter. */ private static class Var extends CounterImpl { public Var(final int missed, final int covered) { super(missed, covered); } @Override public CounterImpl increment(final int missed, final int covered) { this.missed += missed; this.covered += covered; return this; } } /** * Immutable version of the counter. */ private static class Fix extends CounterImpl { public Fix(final int missed, final int covered) { super(missed, covered); } @Override public CounterImpl increment(final int missed, final int covered) { return getInstance(this.missed + missed, this.covered + covered); } } /** * Factory method to retrieve a counter with the given number of items. * * @param missed * number of missed items * @param covered * number of covered items * @return counter instance */ public static CounterImpl getInstance(final int missed, final int covered) { if (missed <= SINGLETON_LIMIT && covered <= SINGLETON_LIMIT) { return SINGLETONS[missed][covered]; } else { return new Var(missed, covered); } } /** * Factory method to retrieve a clone of the given counter. * * @param counter * counter to copy * @return counter instance */ public static CounterImpl getInstance(final ICounter counter) { return getInstance(counter.getMissedCount(), counter.getCoveredCount()); } /** number of missed items */ protected int missed; /** number of covered items */ protected int covered; /** * Creates a new instance with the given numbers. * * @param missed * number of missed items * @param covered * number of covered items */ protected CounterImpl(final int missed, final int covered) { this.missed = missed; this.covered = covered; } /** * Returns a counter with values incremented by the numbers of the given * counter. It is up to the implementation whether this counter instance is * modified or a new instance is returned. * * @param counter * number of additional total and covered items * @return counter instance with incremented values */ public CounterImpl increment(final ICounter counter) { return increment(counter.getMissedCount(), counter.getCoveredCount()); } /** * Returns a counter with values incremented by the given numbers. It is up * to the implementation whether this counter instance is modified or a new * instance is returned. * * @param missed * number of missed items * @param covered * number of covered items * @return counter instance with incremented values */ public abstract CounterImpl increment(int missed, int covered); // === ICounter implementation === public double getValue(final CounterValue value) { switch (value) { case TOTALCOUNT: return getTotalCount(); case MISSEDCOUNT: return getMissedCount(); case COVEREDCOUNT: return getCoveredCount(); case MISSEDRATIO: return getMissedRatio(); case COVEREDRATIO: return getCoveredRatio(); default: throw new AssertionError(value); } } public int getTotalCount() { return missed + covered; } public int getCoveredCount() { return covered; } public int getMissedCount() { return missed; } public double getCoveredRatio() { return (double) covered / (missed + covered); } public double getMissedRatio() { return (double) missed / (missed + covered); } public int getStatus() { int status = covered > 0 ? FULLY_COVERED : EMPTY; if (missed > 0) { status |= NOT_COVERED; } return status; } @Override public boolean equals(final Object obj) { if (obj instanceof ICounter) { final ICounter that = (ICounter) obj; return this.missed == that.getMissedCount() && this.covered == that.getCoveredCount(); } else { return false; } } @Override public int hashCode() { return missed ^ covered * 17; } @Override public String toString() { final StringBuilder b = new StringBuilder("Counter["); //$NON-NLS-1$ b.append(getMissedCount()); b.append('/').append(getCoveredCount()); b.append(']'); return b.toString(); } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/internal/analysis/Instruction.java000066400000000000000000000143551451257705100304200ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import java.util.BitSet; import java.util.Collection; import org.jacoco.core.analysis.ICounter; /** * Execution status of a single bytecode instruction internally used for * coverage analysis. The execution status is recorded separately for each * outgoing branch. Each instruction has at least one branch, for example in * case of a simple sequence of instructions (by convention branch 0). Instances * of this class are used in two steps: * *

Step 1: Building the CFG

* * For each bytecode instruction of a method a {@link Instruction} instance is * created. In correspondence with the CFG these instances are linked with each * other with the addBranch() methods. The executions status is * either directly derived from a probe which has been inserted in the execution * flow ({@link #addBranch(boolean, int)}) or indirectly propagated along the * CFG edges ({@link #addBranch(Instruction, int)}). * *

Step 2: Querying the Coverage Status

* * After all instructions have been created and linked each instruction knows * its execution status and can be queried with: * *
    *
  • {@link #getLine()}
  • *
  • {@link #getInstructionCounter()}
  • *
  • {@link #getBranchCounter()}
  • *
* * For the purpose of filtering instructions can be combined to new * instructions. Note that these methods create new {@link Instruction} * instances and do not modify the existing ones. * *
    *
  • {@link #merge(Instruction)}
  • *
  • {@link #replaceBranches(Collection)}
  • *
*/ public class Instruction { private final int line; private int branches; private final BitSet coveredBranches; private Instruction predecessor; private int predecessorBranch; /** * New instruction at the given line. * * @param line * source line this instruction belongs to */ public Instruction(final int line) { this.line = line; this.branches = 0; this.coveredBranches = new BitSet(); } /** * Adds a branch to this instruction which execution status is indirectly * derived from the execution status of the target instruction. In case the * branch is covered the status is propagated also to the predecessors of * this instruction. * * Note: This method is not idempotent and must be called exactly once for * every branch. * * @param target * target instruction of this branch * @param branch * branch identifier unique for this instruction */ public void addBranch(final Instruction target, final int branch) { branches++; target.predecessor = this; target.predecessorBranch = branch; if (!target.coveredBranches.isEmpty()) { propagateExecutedBranch(this, branch); } } /** * Adds a branch to this instruction which execution status is directly * derived from a probe. In case the branch is covered the status is * propagated also to the predecessors of this instruction. * * Note: This method is not idempotent and must be called exactly once for * every branch. * * @param executed * whether the corresponding probe has been executed * @param branch * branch identifier unique for this instruction */ public void addBranch(final boolean executed, final int branch) { branches++; if (executed) { propagateExecutedBranch(this, branch); } } private static void propagateExecutedBranch(Instruction insn, int branch) { // No recursion here, as there can be very long chains of instructions while (insn != null) { if (!insn.coveredBranches.isEmpty()) { insn.coveredBranches.set(branch); break; } insn.coveredBranches.set(branch); branch = insn.predecessorBranch; insn = insn.predecessor; } } /** * Returns the source line this instruction belongs to. * * @return corresponding source line */ public int getLine() { return line; } /** * Merges information about covered branches of this instruction with * another instruction. * * @param other * instruction to merge with * @return new instance with merged branches */ public Instruction merge(final Instruction other) { final Instruction result = new Instruction(this.line); result.branches = this.branches; result.coveredBranches.or(this.coveredBranches); result.coveredBranches.or(other.coveredBranches); return result; } /** * Creates a copy of this instruction where all outgoing branches are * replaced with the given instructions. The coverage status of the new * instruction is derived from the status of the given instructions. * * @param newBranches * new branches to consider * @return new instance with replaced branches */ public Instruction replaceBranches( final Collection newBranches) { final Instruction result = new Instruction(this.line); result.branches = newBranches.size(); int idx = 0; for (final Instruction b : newBranches) { if (!b.coveredBranches.isEmpty()) { result.coveredBranches.set(idx++); } } return result; } /** * Returns the instruction coverage counter of this instruction. It is * always 1 instruction which is covered or not. * * @return the instruction coverage counter */ public ICounter getInstructionCounter() { return coveredBranches.isEmpty() ? CounterImpl.COUNTER_1_0 : CounterImpl.COUNTER_0_1; } /** * Returns the branch coverage counter of this instruction. Only * instructions with at least 2 outgoing edges report branches. * * @return the branch coverage counter */ public ICounter getBranchCounter() { if (branches < 2) { return CounterImpl.COUNTER_0_0; } final int covered = coveredBranches.cardinality(); return CounterImpl.getInstance(branches - covered, covered); } } jacoco-0.8.11/org.jacoco.core/src/org/jacoco/core/internal/analysis/InstructionsBuilder.java000066400000000000000000000124451451257705100321100ustar00rootroot00000000000000/******************************************************************************* * Copyright (c) 2009, 2023 Mountainminds GmbH & Co. KG and Contributors * This program and the accompanying materials are made available under * the terms of the Eclipse Public License 2.0 which is available at * http://www.eclipse.org/legal/epl-2.0 * * SPDX-License-Identifier: EPL-2.0 * * Contributors: * Marc R. Hoffmann - initial API and implementation * *******************************************************************************/ package org.jacoco.core.internal.analysis; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; import org.jacoco.core.analysis.ISourceNode; import org.jacoco.core.internal.flow.LabelInfo; import org.objectweb.asm.Label; import org.objectweb.asm.tree.AbstractInsnNode; /** * Stateful builder for the {@link Instruction}s of a method. All instructions * of a method must be added in their original sequence along with additional * information like line numbers. Afterwards the instructions can be obtained * with the getInstructions() method. */ class InstructionsBuilder { /** Probe array of the class the analyzed method belongs to. */ private final boolean[] probes; /** The line which belong to subsequently added instructions. */ private int currentLine; /** The last instruction which has been added. */ private Instruction currentInsn; /** * All instructions of a method mapped from the ASM node to the * corresponding {@link Instruction} instance. */ private final Map instructions; /** * The labels which mark the subsequent instructions. * * Due to ASM issue #315745 there can be more than one label per instruction */ private final List