1/*
2 * Copyright (c) 2016, 2019, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 */
23
24#include "precompiled.hpp"
25#include "jvm.h"
26#include "logTestFixture.hpp"
27#include "logTestUtils.inline.hpp"
28#include "logging/logConfiguration.hpp"
29#include "logging/logOutput.hpp"
30#include "memory/allocation.inline.hpp"
31#include "memory/resourceArea.hpp"
32#include "unittest.hpp"
33#include "utilities/ostream.hpp"
34
35LogTestFixture::LogTestFixture() : _n_snapshots(0), _configuration_snapshot(NULL) {
36
37 // Set up TestLogFileName to include temp_dir, PID, testcase name and test name.
38 const testing::TestInfo* test_info = ::testing::UnitTest::GetInstance()->current_test_info();
39 int ret = jio_snprintf(_filename, sizeof(_filename), "%s%stestlog.pid%d.%s.%s.log",
40 os::get_temp_directory(), os::file_separator(), os::current_process_id(),
41 test_info->test_case_name(), test_info->name());
42 EXPECT_GT(ret, 0) << "_filename buffer issue";
43 TestLogFileName = _filename;
44
45 snapshot_config();
46}
47
48LogTestFixture::~LogTestFixture() {
49 restore_config();
50 clear_snapshot();
51 delete_file(TestLogFileName);
52}
53
54bool LogTestFixture::set_log_config(const char* output,
55 const char* what,
56 const char* decorators,
57 const char* options,
58 bool allow_failure) {
59 ResourceMark rm;
60 stringStream stream;
61 bool success = LogConfiguration::parse_log_arguments(output, what, decorators, options, &stream);
62 if (!allow_failure) {
63 const char* errmsg = stream.as_string();
64 EXPECT_STREQ("", errmsg) << "Unexpected error reported";
65 EXPECT_TRUE(success) << "Shouldn't cause errors";
66 }
67 return success;
68}
69
70void LogTestFixture::snapshot_config() {
71 clear_snapshot();
72 _n_snapshots = LogConfiguration::_n_outputs;
73 _configuration_snapshot = NEW_C_HEAP_ARRAY(char*, _n_snapshots, mtLogging);
74 for (size_t i = 0; i < _n_snapshots; i++) {
75 ResourceMark rm;
76 stringStream ss;
77 LogConfiguration::_outputs[i]->describe(&ss);
78 _configuration_snapshot[i] = os::strdup_check_oom(ss.as_string(), mtLogging);
79 }
80}
81
82void LogTestFixture::restore_config() {
83 LogConfiguration::disable_logging();
84 for (size_t i = 0; i < _n_snapshots; i++) {
85 // Restore the config based on the saved output description string.
86 // The string has the following format: '<name> <selection> <decorators>[ <options>]'
87 // Extract the different parameters by replacing the spaces with NULLs.
88 char* str = _configuration_snapshot[i];
89
90 char* name = str;
91 str = strchr(str, ' ');
92 *str++ = '\0';
93
94 char* selection = str;
95 str = strchr(str, ' ');
96 *str++ = '\0';
97
98 char* decorators = str;
99
100 char* options = NULL;
101 str = strchr(str, ' ');
102 if (str != NULL) {
103 *str++ = '\0';
104 options = str;
105 }
106
107 set_log_config(name, selection, decorators, options != NULL ? options : "");
108 }
109}
110
111void LogTestFixture::clear_snapshot() {
112 if (_configuration_snapshot == NULL) {
113 return;
114 }
115 assert(_n_snapshots > 0, "non-null array should have at least 1 element");
116 for (size_t i = 0; i < _n_snapshots; i++) {
117 os::free(_configuration_snapshot[i]);
118 }
119 FREE_C_HEAP_ARRAY(char*, _configuration_snapshot);
120 _configuration_snapshot = NULL;
121 _n_snapshots = 0;
122}
123