Path: blob/master/test/functional/RasapiTest/src/com/ibm/dump/tests/OutputFile.java
6007 views
/*******************************************************************************1* Copyright (c) 2016, 2021 IBM Corp. and others2*3* This program and the accompanying materials are made available under4* the terms of the Eclipse Public License 2.0 which accompanies this5* distribution and is available at https://www.eclipse.org/legal/epl-2.0/6* or the Apache License, Version 2.0 which accompanies this distribution and7* is available at https://www.apache.org/licenses/LICENSE-2.0.8*9* This Source Code may also be made available under the following10* Secondary Licenses when the conditions for such availability set11* forth in the Eclipse Public License, v. 2.0 are satisfied: GNU12* General Public License, version 2 with the GNU Classpath13* Exception [1] and GNU General Public License, version 2 with the14* OpenJDK Assembly Exception [2].15*16* [1] https://www.gnu.org/software/classpath/license.html17* [2] http://openjdk.java.net/legal/assembly-exception.html18*19* SPDX-License-Identifier: EPL-2.0 OR Apache-2.0 OR GPL-2.0 WITH Classpath-exception-2.0 OR LicenseRef-GPL-2.0 WITH Assembly-exception20*******************************************************************************/21package com.ibm.dump.tests;2223import java.io.BufferedReader;24import java.io.FileReader;25import java.io.IOException;26import java.util.ArrayList;2728public class OutputFile {2930BufferedReader in;31String line;32String firstReference;33String secondReference;3435public OutputFile(String fileName) throws IOException {36in = new BufferedReader(new FileReader(fileName));37firstReference = null;38}3940/**41* Yes, finalizers may not have a very good reputation but it can't do any harm42*/43protected void finalize() throws Throwable {44try {45in.close();46} finally {47super.finalize();48}49}505152/**53* Read through the file looking for the given string. Keep going to the end of the file if necessary.54* If the string is found, return true, set the instance variable line, and keep that position in the file.55* If the string is not found, return false, leave the file positioned at the end.5657* @param lookFor the string to look for58* @return true or false according to whether a line with the string was found59* @throws IOException60*/61public boolean skipUnlimitedToLineContaining(String lookFor) throws IOException {62line = in.readLine();63while (line != null) {64if (line.indexOf(lookFor) != -1) {65System.err.printf("Successfully found the following line containing \"%s\"\n", lookFor);66System.err.printf(line);67System.err.printf("\n");68return true;69}70line = in.readLine();71}72System.err.printf("***Reached end of file before finding a line containing \"%s\"\n", lookFor);73return false;74}7576/**77* Read through the file looking for the given string. Keep going to the end of the file if necessary.78* If the string is found AT THE END OF THE LINE, return true, set the instance variable line, and keep that position in the file.79* If the string is not found, return false, leave the file positioned at the end.80*81* This method is especially for searching for the line ending "OBJ com/ibm/dump/tests/types/packed/NestedPacked" in the82* classic heapdump. Just using skipUnlimitedToLineContaining finds the lines for NestedPacked1 and NestedPacked28384* @param lookFor the string to look for85* @return true or false according to whether a line with the string was found86* @throws IOException87*/88public boolean skipUnlimitedToLineEnding(String lookFor) throws IOException {89line = in.readLine();90while (line != null) {91if (line.endsWith(lookFor)) {92System.err.printf("Successfully found the following line ending \"%s\"\n", lookFor);93System.err.printf(line);94System.err.printf("\n");95return true;96}97line = in.readLine();98}99System.err.printf("***Reached end of file before finding a line ending \"%s\"\n", lookFor);100return false;101}102103/**104* Read no more than maxLinesToSkip down the file looking for a line containing the given string105* Read some number of lines down the file looking for the given string. Read no more than maxLinesToSkip lines.106* If the string is found, hold the line in instance variable line and keep the position in the file.107* If the string is not found, return false and restore the position in the file to where it was on entry:108* by doing so one failing test does not damage the tests that follow.109* @param maxLinesToSkip skip no more lines than this110* @param lookFor the string to look for111* @return true or false according to whether a line with the string was found112* @throws IOException113*/114public boolean skipLimitedToLineContaining(int maxLinesToSkip, String lookFor) throws IOException {115int linesRead = 0;116in.mark(maxLinesToSkip * 200); // generous allocation to allow reset to work. Most lines are < 100 bytes long117line = in.readLine();118while (line != null && linesRead < maxLinesToSkip) {119// System.err.printf("line read was %s\n", line);120if (line.indexOf(lookFor) != -1) {121System.err.printf("Successfully found a line containing \"%s\"\n", lookFor);122return true;123}124line = in.readLine();125linesRead++;126}127System.err.printf("***Failed to find a line containing \"%s\"\n", lookFor);128in.reset();129return false;130}131132133/**134* Examine the last line read and check that the word at the given position is equal to given string135* @param lookFor the string to look for136* @param whichWord the index of the word to check137* @return138*/139public boolean linePassesCheckForStringAtWord(String lookFor, int whichWord) {140if (line == null) {141// previous call to skip[Un]limitedToLineContaining has failed142// so appropriate error message has been emitted already143// just return false and allow test to contine.144return false;145}146return StringUtils.linePassesCheckForStringAtWord(line, whichWord, lookFor);147}148149/**150* Return true or false depending on whether the word at position whichWord is in the list151* of values in validValues152*153* @param validValues154* @param whichWord155* @return156*/157public boolean linePassesCheckForStringsAtWord(String[] validValues, int whichWord) {158if (line == null) {159// previous call to skip[Un]limitedToLineContaining has failed160// so appropriate error message has been emitted already161// just return false and allow test to contine.162return false;163}164return StringUtils.linePassesCheckForStringsAtWord(line, whichWord, validValues);165}166167/**168*169* @return the first reference that was found by the previous call to skipToNextLineAndCheckReferencesCount.170* This is just the first token that was on that line.171*/172public String getFirstReference() {173return firstReference;174}175176/**177*178* @return the second reference that was found by the previous call to skipToNextLineAndCheckReferencesCount.179* This is just the second token that was on that line.180*/181public String getSecondReference() {182return secondReference;183}184185/**186* Skip down to the lines containing "references:" then check the number of references on the187* succeeding line.188* @param maxLinesToSkip189* @param expectedNumberOfReferences190* @return true or false depending on whether the number of references matches the expected number.191* @throws IOException192*/193public boolean skipToLineContainingListOfReferencesAndCheckCount(int maxLinesToSkip, int expectedNumberOfReferences) throws IOException {194195if (! skipLimitedToLineContaining(maxLinesToSkip, "references:")) {196// if we cannot find the references line, don't go further197return false;198}199return skipToNextLineAndCheckReferencesCount(expectedNumberOfReferences);200201}202203/**204* Skip down the output from jdmpview's x/j command looking for the line containing "references:"205* @param maxLinesToSkip206* @return207* @throws IOException208*/209public boolean skipLimitedToReferencesLine(int maxLinesToSkip) throws IOException {210if (! skipLimitedToLineContaining(maxLinesToSkip, "references:")) {211// if we cannot find the references line, don't go further212return false;213}214return true;215}216217/**218* Read the next line, tokenise it, and check that the number of tokens equals the given parameter.219* As a side effect, set the instance variable firstReference.220*221* This method can be called either from the classic heapdump checkers, when the file will be already222* positioned on the OBJ line and the references always come on the next line,223* or called from skipToLineContainingListOfReferencesAndCheckCount() when checking the224* output from jdmpview's x/j command. In either case, the list of references is on the very next line.225*226*227*228* @param expectedNumberOfReferences229* @return true or false depending on whether the line does or does not contain the given number of tokens.230* @throws IOException231*/232public boolean skipToNextLineAndCheckReferencesCount(int expectedNumberOfReferences) throws IOException {233// assert234// if we are called by one of the classic heapdump checkers we are currently on the OBJ line and235// skipping to the next line will put us on the list of references, or236// we will have been called from skipToReferencesLineAndCheckCount if we are checking the output237// from jdmpview's x/j command during phd checking238239240String line = in.readLine();241if (line == null) {242System.err.println("***Unable to check count of references - previous call to find the references lines has failed.");243return false;244}245246ArrayList<String> references = StringUtils.extractTokensFromLine(line);247if (references.size() > 0) {248firstReference = references.get(0);249} else {250firstReference = null;251}252if (references.size() > 1) {253secondReference = references.get(1);254} else {255secondReference = null;256}257if (references.size() != expectedNumberOfReferences) {258System.err.println("***Failure: there should have been exactly " + expectedNumberOfReferences + " reference(s), not " + references.size());259return false;260} else {261System.err.println("Successfully found exactly " + expectedNumberOfReferences + " reference(s)");262return true;263}264}265266/**267* Read the next line, tokenise it, and return the the number of tokens (references).268*269* This method is called from the classic heapdump checkers, when the file will be already270* positioned on the OBJ line and the references always come on the next line271*272* @return number of references273* @throws IOException274*/275public int skipToNextLineAndCountReferences() throws IOException {276// if we are called by one of the classic heapdump checkers we are currently on the OBJ line and277// skipping to the next line will put us on the list of references278String line = in.readLine();279if (line == null) {280System.err.println("***Unable to check count of references - previous call to find the references lines has failed.");281return 0;282}283284ArrayList<String> references = StringUtils.extractTokensFromLine(line);285return references.size();286}287288public static boolean checkReferenceInClassicHeapdumpIsToObject(String fileName, String reference, String className) throws IOException {289OutputFile o = new OutputFile(fileName);290boolean passed = true;291System.err.println("Checking that the reference " + reference + " is to an object of type " + className);292passed &= o.skipUnlimitedToLineBeginning(reference);293passed &= o.linePassesCheckForStringAtWord(className,4);294return passed;295}296297private boolean skipUnlimitedToLineBeginning(String lookFor) throws IOException {298line = in.readLine();299while (line != null) {300if (line.startsWith(lookFor) ) {301System.err.printf("Successfully found a line beginning \"%s\"\n", lookFor);302System.err.printf(line);303System.err.printf("\n");304return true;305}306line = in.readLine();307}308System.err.printf("***Reached end of file before finding a line beginning \"%s\"\n", lookFor);309return false;310}311312public static boolean checkReferenceIsToObject(String fileName, String reference, String className) throws IOException {313OutputFile o = new OutputFile(fileName);314boolean passed = true;315System.err.println("Checking that the reference " + reference + " is to an object of type " + className);316passed &= o.skipUnlimitedToLineContaining(className + " @ " + reference);317return passed;318}319320}321322323324