Improve coding style in testutils.cpp
This commit is contained in:
parent
0f45817956
commit
f50321f414
|
@ -211,18 +211,19 @@ string TestApplication::workingCopyPathMode(const string &name, WorkingCopyMode
|
|||
{
|
||||
// ensure working directory is present
|
||||
struct stat currentStat;
|
||||
if (stat(m_workingDir.c_str(), ¤tStat) || !S_ISDIR(currentStat.st_mode)) {
|
||||
if (mkdir(m_workingDir.c_str(), S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH)) {
|
||||
cerr << Phrases::Error << "Unable to create working copy for \"" << name << "\": can't create working directory." << Phrases::EndFlush;
|
||||
return string();
|
||||
}
|
||||
if ((stat(m_workingDir.c_str(), ¤tStat) || !S_ISDIR(currentStat.st_mode))
|
||||
&& mkdir(m_workingDir.c_str(), S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH)) {
|
||||
cerr << Phrases::Error << "Unable to create working copy for \"" << name << "\": can't create working directory." << Phrases::EndFlush;
|
||||
return string();
|
||||
}
|
||||
|
||||
// ensure subdirectory exists
|
||||
const auto parts = splitString<vector<string>>(name, string("/"), EmptyPartsTreat::Omit);
|
||||
const auto parts = splitString<vector<string>>(name, "/", EmptyPartsTreat::Omit);
|
||||
if (!parts.empty()) {
|
||||
string currentLevel = m_workingDir;
|
||||
// create subdirectory level by level
|
||||
string currentLevel;
|
||||
currentLevel.reserve(m_workingDir.size() + name.size() + 1);
|
||||
currentLevel.assign(m_workingDir);
|
||||
for (auto i = parts.cbegin(), end = parts.end() - 1; i != end; ++i) {
|
||||
if (currentLevel.back() != '/') {
|
||||
currentLevel += '/';
|
||||
|
@ -238,8 +239,7 @@ string TestApplication::workingCopyPathMode(const string &name, WorkingCopyMode
|
|||
continue;
|
||||
}
|
||||
// fail otherwise
|
||||
cerr << Phrases::Error << "Unable to create working copy for \"" << name << "\": can't create working directory."
|
||||
<< Phrases::EndFlush;
|
||||
cerr << Phrases::Error << "Unable to create working copy for \"" << name << "\": can't create working directory." << Phrases::EndFlush;
|
||||
return string();
|
||||
}
|
||||
}
|
||||
|
@ -255,12 +255,14 @@ string TestApplication::workingCopyPathMode(const string &name, WorkingCopyMode
|
|||
fstream origFile, workingCopy;
|
||||
origFile.open(origFilePath, ios_base::in | ios_base::binary);
|
||||
if (origFile.fail()) {
|
||||
cerr << Phrases::Error << "Unable to create working copy for \"" << name << "\": an IO error occurred when opening original file \"" << origFilePath << "\"." << Phrases::EndFlush;
|
||||
cerr << Phrases::Error << "Unable to create working copy for \"" << name << "\": an IO error occurred when opening original file \""
|
||||
<< origFilePath << "\"." << Phrases::EndFlush;
|
||||
return string();
|
||||
}
|
||||
workingCopy.open(workingCopyPath, ios_base::out | ios_base::binary | ios_base::trunc);
|
||||
if (workingCopy.fail()) {
|
||||
cerr << Phrases::Error << "Unable to create working copy for \"" << name << "\": an IO error occurred when opening target file \"" << workingCopyPath << "\"." << Phrases::EndFlush;
|
||||
cerr << Phrases::Error << "Unable to create working copy for \"" << name << "\": an IO error occurred when opening target file \""
|
||||
<< workingCopyPath << "\"." << Phrases::EndFlush;
|
||||
return string();
|
||||
}
|
||||
workingCopy << origFile.rdbuf();
|
||||
|
@ -270,7 +272,7 @@ string TestApplication::workingCopyPathMode(const string &name, WorkingCopyMode
|
|||
|
||||
cerr << Phrases::Error << "Unable to create working copy for \"" << name << "\": ";
|
||||
if (origFile.fail()) {
|
||||
cerr << "an IO error occurred when reading original file \"" << origFilePath << "\"";
|
||||
cerr << "an IO error occurred when reading original file \"" << origFilePath << "\"";
|
||||
return string();
|
||||
}
|
||||
if (workingCopy.fail()) {
|
||||
|
@ -312,14 +314,16 @@ int execAppInternal(const char *appPath, const char *const *args, std::string &o
|
|||
|
||||
// create pipes
|
||||
int coutPipes[2], cerrPipes[2];
|
||||
pipe(coutPipes), pipe(cerrPipes);
|
||||
int readCoutPipe = coutPipes[0], writeCoutPipe = coutPipes[1];
|
||||
int readCerrPipe = cerrPipes[0], writeCerrPipe = cerrPipes[1];
|
||||
pipe(coutPipes);
|
||||
pipe(cerrPipes);
|
||||
const auto readCoutPipe = coutPipes[0], writeCoutPipe = coutPipes[1];
|
||||
const auto readCerrPipe = cerrPipes[0], writeCerrPipe = cerrPipes[1];
|
||||
|
||||
// create child process
|
||||
if (int child = fork()) {
|
||||
if (const auto child = fork()) {
|
||||
// parent process: read stdout and stderr from child
|
||||
close(writeCoutPipe), close(writeCerrPipe);
|
||||
close(writeCoutPipe);
|
||||
close(writeCerrPipe);
|
||||
|
||||
try {
|
||||
if (child == -1) {
|
||||
|
@ -334,41 +338,41 @@ int execAppInternal(const char *appPath, const char *const *args, std::string &o
|
|||
|
||||
// init variables for reading
|
||||
char buffer[512];
|
||||
ssize_t count;
|
||||
output.clear(), errors.clear();
|
||||
output.clear();
|
||||
errors.clear();
|
||||
|
||||
// poll as long as at least one pipe is open
|
||||
do {
|
||||
int retpoll = poll(fileDescriptorSet, 2, timeout);
|
||||
if (retpoll > 0) {
|
||||
// poll succeeds
|
||||
if (fileDescriptorSet[0].revents & POLLIN) {
|
||||
if ((count = read(readCoutPipe, buffer, sizeof(buffer))) > 0) {
|
||||
output.append(buffer, static_cast<size_t>(count));
|
||||
}
|
||||
} else if (fileDescriptorSet[0].revents & POLLHUP) {
|
||||
close(readCoutPipe);
|
||||
fileDescriptorSet[0].fd = -1;
|
||||
}
|
||||
if (fileDescriptorSet[1].revents & POLLIN) {
|
||||
if ((count = read(readCerrPipe, buffer, sizeof(buffer))) > 0) {
|
||||
errors.append(buffer, static_cast<size_t>(count));
|
||||
}
|
||||
} else if (fileDescriptorSet[1].revents & POLLHUP) {
|
||||
close(readCerrPipe);
|
||||
fileDescriptorSet[1].fd = -1;
|
||||
}
|
||||
} else if (retpoll == 0) {
|
||||
// timeout
|
||||
const auto retpoll = poll(fileDescriptorSet, 2, timeout);
|
||||
if (retpoll == 0) {
|
||||
throw runtime_error("Poll time-out");
|
||||
} else {
|
||||
// fail
|
||||
}
|
||||
if (retpoll < 0) {
|
||||
throw runtime_error("Poll failed");
|
||||
}
|
||||
if (fileDescriptorSet[0].revents & POLLIN) {
|
||||
const auto count = read(readCoutPipe, buffer, sizeof(buffer));
|
||||
if (count > 0) {
|
||||
output.append(buffer, static_cast<size_t>(count));
|
||||
}
|
||||
} else if (fileDescriptorSet[0].revents & POLLHUP) {
|
||||
close(readCoutPipe);
|
||||
fileDescriptorSet[0].fd = -1;
|
||||
}
|
||||
if (fileDescriptorSet[1].revents & POLLIN) {
|
||||
const auto count = read(readCerrPipe, buffer, sizeof(buffer));
|
||||
if (count > 0) {
|
||||
errors.append(buffer, static_cast<size_t>(count));
|
||||
}
|
||||
} else if (fileDescriptorSet[1].revents & POLLHUP) {
|
||||
close(readCerrPipe);
|
||||
fileDescriptorSet[1].fd = -1;
|
||||
}
|
||||
} while (fileDescriptorSet[0].fd >= 0 || fileDescriptorSet[1].fd >= 0);
|
||||
} catch (...) {
|
||||
// ensure all pipes are close in the error case
|
||||
close(readCoutPipe), close(readCerrPipe);
|
||||
// ensure all pipes are closed in the error case
|
||||
close(readCoutPipe);
|
||||
close(readCerrPipe);
|
||||
throw;
|
||||
}
|
||||
|
||||
|
@ -379,8 +383,12 @@ int execAppInternal(const char *appPath, const char *const *args, std::string &o
|
|||
} else {
|
||||
// child process
|
||||
// -> set pipes to be used for stdout/stderr
|
||||
dup2(writeCoutPipe, STDOUT_FILENO), dup2(writeCerrPipe, STDERR_FILENO);
|
||||
close(readCoutPipe), close(writeCoutPipe), close(readCerrPipe), close(writeCerrPipe);
|
||||
dup2(writeCoutPipe, STDOUT_FILENO);
|
||||
dup2(writeCerrPipe, STDERR_FILENO);
|
||||
close(readCoutPipe);
|
||||
close(writeCoutPipe);
|
||||
close(readCerrPipe);
|
||||
close(writeCerrPipe);
|
||||
|
||||
// -> modify environment variable LLVM_PROFILE_FILE to apply new path for profiling output
|
||||
if (!newProfilingPath.empty()) {
|
||||
|
@ -475,7 +483,7 @@ string TestApplication::readTestfilePathFromSrcRef()
|
|||
try {
|
||||
// read "srcdirref" file which should contain the path of the source directory; this file should have been
|
||||
// create by the CMake module "TestTarget.cmake"
|
||||
string srcDirContent(readFile("srcdirref", 2 * 1024));
|
||||
auto srcDirContent(readFile("srcdirref", 2 * 1024));
|
||||
if (srcDirContent.empty()) {
|
||||
cerr << Phrases::Warning << "The file \"srcdirref\" is empty." << Phrases::EndFlush;
|
||||
return string();
|
||||
|
|
Loading…
Reference in New Issue