Move duplicated test code into shared modules (#220)

Move common testing code which doesn't need linking with GParted objects
into the common module.  Move the remaining common code used to print
GParted objects using the insertion operator (operator<<) into the
insertion_operators module.  Split the common code like this so that the
operator<<(std::ostream&, const OperationDetail&) function is not
included in test_PipeCapture and it is not forced to link with all the
non-UI related GParted objects.

The Automake manual provides guidance that when a header belongs to a
single program it is recommended to be listed in the program's _SOURCES
variable and for a directory only containing header files listing them
in the noinst_HEADERS variable is the right variable to use [1].
However the guidance doesn't cover this case for common.h and
insertion_operators.h; header files in a directory with other files and
used by multiple programs.  So just because we have gparted_core_OBJECTS
(normal Makefile, not Automake special variable) listing objects to link
with, choose to use noinst_HEADERS Automake variable to list needed
headers.

[1] GNU Automake manual, 9.2 Header files
    https://www.gnu.org/software/automake/manual/html_node/Headers.html
        "Usually, only header files that accompany installed libraries
        need to be installed.  Headers used by programs or convenience
        libraries are not installed.  The noinst_HEADERS variable can be
        used for such headers.  However, when the header belongs to a
        single convenience library or program, we recommend listing it
        in the program's or library's _SOURCES variable (see Defining
        program sources) instead of in noinst_HEADERS.  This is clearer
        for the Makefile.am reader.  noinst_HEADERS would be the right
        variable to use in a directory containing only headers and no
        associated library or program.

        All header files must be listed somewhere; in a _SOURCES
        variable or in a _HEADERS variable.  Missing ones will not
        appear in the distribution.
        "

Closes #220 - Format to Cleared not clearing "pdc" ataraid signature
This commit is contained in:
Mike Fleetwood 2023-02-05 11:16:43 +00:00 committed by Curtis Gedak
parent 4ce37d4fde
commit 8ec302e1b0
8 changed files with 346 additions and 343 deletions

View File

@ -21,6 +21,10 @@ check_PROGRAMS = \
# Test cases to be run by "make check" # Test cases to be run by "make check"
TESTS = $(check_PROGRAMS) TESTS = $(check_PROGRAMS)
noinst_HEADERS = \
common.h \
insertion_operators.h
gparted_core_OBJECTS = \ gparted_core_OBJECTS = \
$(top_builddir)/src/BCache_Info.$(OBJEXT) \ $(top_builddir)/src/BCache_Info.$(OBJEXT) \
$(top_builddir)/src/BlockSpecial.$(OBJEXT) \ $(top_builddir)/src/BlockSpecial.$(OBJEXT) \
@ -72,7 +76,10 @@ test_BlockSpecial_LDADD = \
$(top_builddir)/src/BlockSpecial.$(OBJEXT) \ $(top_builddir)/src/BlockSpecial.$(OBJEXT) \
$(LDADD) $(LDADD)
test_EraseFileSystemSignatures_SOURCES = test_EraseFileSystemSignatures.cc test_EraseFileSystemSignatures_SOURCES = \
test_EraseFileSystemSignatures.cc \
common.cc \
insertion_operators.cc
test_EraseFileSystemSignatures_LDADD = \ test_EraseFileSystemSignatures_LDADD = \
$(gparted_core_OBJECTS) \ $(gparted_core_OBJECTS) \
$(GTEST_LIBS) \ $(GTEST_LIBS) \
@ -83,12 +90,17 @@ test_PasswordRAMStore_LDADD = \
$(top_builddir)/src/PasswordRAMStore.$(OBJEXT) \ $(top_builddir)/src/PasswordRAMStore.$(OBJEXT) \
$(LDADD) $(LDADD)
test_PipeCapture_SOURCES = test_PipeCapture.cc test_PipeCapture_SOURCES = \
test_PipeCapture.cc \
common.cc
test_PipeCapture_LDADD = \ test_PipeCapture_LDADD = \
$(top_builddir)/src/PipeCapture.$(OBJEXT) \ $(top_builddir)/src/PipeCapture.$(OBJEXT) \
$(LDADD) $(LDADD)
test_SupportedFileSystems_SOURCES = test_SupportedFileSystems.cc test_SupportedFileSystems_SOURCES = \
test_SupportedFileSystems.cc \
common.cc \
insertion_operators.cc
test_SupportedFileSystems_LDADD = \ test_SupportedFileSystems_LDADD = \
$(gparted_core_OBJECTS) \ $(gparted_core_OBJECTS) \
$(GTEST_LIBS) \ $(GTEST_LIBS) \

115
tests/common.cc Normal file
View File

@ -0,0 +1,115 @@
/* Copyright (C) 2023 Mike Fleetwood
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, see <http://www.gnu.org/licenses/>.
*/
#include "common.h"
#include <iostream>
#include <sstream>
#include <string>
#include <iomanip>
#include <stddef.h>
#include <ctype.h>
#include <stdlib.h>
#include <stdio.h>
#include <errno.h>
#include <string.h>
#include <unistd.h>
namespace GParted
{
// Format up to BinaryStringChunkSize (16) bytes of binary data ready for printing as:
// Hex offset ASCII text Hex bytes
// "0x000000000 \"ABCDEFGHabcdefgh\" 41 42 43 44 45 46 47 48 61 62 63 64 65 66 67 68"
std::string binary_string_to_print(size_t offset, const char* s, size_t len)
{
std::ostringstream result;
result << "0x";
result.fill('0');
result << std::setw(8) << std::hex << std::uppercase << offset << " \"";
size_t i;
for (i = 0; i < BinaryStringChunkSize && i < len; i++)
result.put((isprint(s[i])) ? s[i] : '.');
result.put('\"');
if (len > 0)
{
for (; i < BinaryStringChunkSize; i++)
result.put(' ');
result.put(' ');
for (i = 0 ; i < BinaryStringChunkSize && i < len; i++)
result << " "
<< std::setw(2) << std::hex << std::uppercase
<< (unsigned int)(unsigned char)s[i];
}
return result.str();
}
// Re-execute current executable using xvfb-run so that it provides a virtual X11 display.
static void exec_using_xvfb_run(int argc, char** argv)
{
// argc+2 = Space for "xvfb-run" command, existing argc strings plus NULL pointer.
size_t size = sizeof(char*) * (argc+2);
char** new_argv = (char**)malloc(size);
if (new_argv == NULL)
{
fprintf(stderr, "Failed to allocate %lu bytes of memory. errno=%d,%s\n",
(unsigned long)size, errno, strerror(errno));
exit(EXIT_FAILURE);
}
new_argv[0] = strdup("xvfb-run");
if (new_argv[0] == NULL)
{
fprintf(stderr, "Failed to allocate %lu bytes of memory. errno=%d,%s\n",
(unsigned long)strlen(new_argv[0])+1, errno, strerror(errno));
exit(EXIT_FAILURE);
}
// Copy argv pointers including final NULL pointer.
for (size_t i = 0; i <= (unsigned)argc; i++)
new_argv[i+1] = argv[i];
execvp(new_argv[0], new_argv);
fprintf(stderr, "Failed to execute '%s %s ...'. errno=%d,%s\n", new_argv[0], new_argv[1],
errno, strerror(errno));
exit(EXIT_FAILURE);
}
// Ensure there is an X11 display, providing a virtual one if needed.
void ensure_x11_display(int argc, char** argv)
{
const char* display = getenv("DISPLAY");
if (display == NULL)
{
printf("DISPLAY environment variable unset. Executing 'xvfb-run %s ...'\n", argv[0]);
exec_using_xvfb_run(argc, argv);
}
printf("DISPLAY=\"%s\"\n", display);
}
} //GParted

43
tests/common.h Normal file
View File

@ -0,0 +1,43 @@
/* Copyright (C) 2023 Mike Fleetwood
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, see <http://www.gnu.org/licenses/>.
*/
/* common
*
* Common functions used in testing that don't depend on any GParted code so don't require
* any GParted objects to need to be linked in order to be used.
*/
#ifndef GPARTED_TEST_COMMON_H
#define GPARTED_TEST_COMMON_H
#include <stddef.h>
#include <string>
namespace GParted
{
const size_t BinaryStringChunkSize = 16;
std::string binary_string_to_print(size_t offset, const char* s, size_t len);
void ensure_x11_display(int argc, char** argv);
} // namespace GParted
#endif /* GPARTED_TEST_COMMON_H */

View File

@ -0,0 +1,120 @@
/* Copyright (C) 2023 Mike Fleetwood
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, see <http://www.gnu.org/licenses/>.
*/
#include "insertion_operators.h"
#include "OperationDetail.h"
#include <iostream>
#include <stddef.h>
#include <glibmm/ustring.h>
namespace GParted
{
// Hacky XML parser which strips italic and bold markup added in
// OperationDetail::set_description() and reverts just these 5 characters &<>'" encoded by
// Glib::Markup::escape_text() -> g_markup_escape_text() -> append_escaped_text().
static Glib::ustring strip_markup(const Glib::ustring& str)
{
size_t len = str.length();
size_t i = 0;
Glib::ustring ret;
ret.reserve(len);
while (i < len)
{
if (str.compare(i, 3, "<i>") == 0)
i += 3;
else if (str.compare(i, 4, "</i>") == 0)
i += 4;
else if (str.compare(i, 3, "<b>") == 0)
i += 3;
else if (str.compare(i, 4, "</b>") == 0)
i += 4;
else if (str.compare(i, 5, "&amp;") == 0)
{
ret.push_back('&');
i += 5;
}
else if (str.compare(i, 4, "&lt;") == 0)
{
ret.push_back('<');
i += 4;
}
else if (str.compare(i, 4, "&gt;") == 0)
{
ret.push_back('>');
i += 4;
}
else if (str.compare(i, 6, "&apos;") == 0)
{
ret.push_back('\'');
i += 6;
}
else if (str.compare(i, 6, "&quot;") == 0)
{
ret.push_back('"');
i += 6;
}
else
{
ret.push_back(str[i]);
i++;
}
}
return ret;
}
// Print method for OperationDetailStatus.
std::ostream& operator<<(std::ostream& out, const OperationDetailStatus od_status)
{
switch (od_status)
{
case STATUS_NONE: out << "NONE"; break;
case STATUS_EXECUTE: out << "EXECUTE"; break;
case STATUS_SUCCESS: out << "SUCCESS"; break;
case STATUS_ERROR: out << "ERROR"; break;
case STATUS_INFO: out << "INFO"; break;
case STATUS_WARNING: out << "WARNING"; break;
default: break;
}
return out;
}
// Print method for an OperationDetail object.
std::ostream& operator<<(std::ostream& out, const OperationDetail& od)
{
out << strip_markup(od.get_description());
Glib::ustring elapsed = od.get_elapsed_time();
if (! elapsed.empty())
out << " " << elapsed;
if (od.get_status() != STATUS_NONE)
out << " (" << od.get_status() << ")";
out << "\n";
for (size_t i = 0; i < od.get_childs().size(); i++)
{
out << *od.get_childs()[i];
}
return out;
}
} //GParted

View File

@ -0,0 +1,42 @@
/* Copyright (C) 2023 Mike Fleetwood
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, see <http://www.gnu.org/licenses/>.
*/
/* insertion_operators
*
* Insertion operators for various GParted object types which print the object to an
* output stream.
*/
#ifndef GPARTED_TEST_INSERTION_OPERATORS_H
#define GPARTED_TEST_INSERTION_OPERATORS_H
#include "OperationDetail.h"
#include <iostream>
namespace GParted
{
std::ostream& operator<<(std::ostream& out, const OperationDetailStatus od_status);
std::ostream& operator<<(std::ostream& out, const OperationDetail& od);
} // namespace GParted
#endif /* GPARTED_TEST_INSERTION_OPERATORS_H */

View File

@ -18,19 +18,15 @@
*/ */
#include "common.h"
#include "insertion_operators.h"
#include "GParted_Core.h" #include "GParted_Core.h"
#include "OperationDetail.h" #include "OperationDetail.h"
#include "Partition.h" #include "Partition.h"
#include "Utils.h" #include "Utils.h"
#include "gtest/gtest.h" #include "gtest/gtest.h"
#include <iostream>
#include <fstream>
#include <sstream>
#include <string>
#include <iomanip>
#include <stddef.h> #include <stddef.h>
#include <ctype.h>
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <errno.h> #include <errno.h>
@ -40,7 +36,6 @@
#include <unistd.h> #include <unistd.h>
#include <gtkmm.h> #include <gtkmm.h>
#include <parted/parted.h> #include <parted/parted.h>
#include <glibmm/ustring.h>
#include <glibmm/thread.h> #include <glibmm/thread.h>
@ -48,96 +43,6 @@ namespace GParted
{ {
// Hacky XML parser which strips italic and bold markup added in
// OperationDetail::set_description() and reverts just these 5 characters &<>'" encoded by
// Glib::Markup::escape_text() -> g_markup_escape_text() -> append_escaped_text().
Glib::ustring strip_markup(const Glib::ustring& str)
{
size_t len = str.length();
size_t i = 0;
Glib::ustring ret;
ret.reserve(len);
while (i < len)
{
if (str.compare(i, 3, "<i>") == 0)
i += 3;
else if (str.compare(i, 4, "</i>") == 0)
i += 4;
else if (str.compare(i, 3, "<b>") == 0)
i += 3;
else if (str.compare(i, 4, "</b>") == 0)
i += 4;
else if (str.compare(i, 5, "&amp;") == 0)
{
ret.push_back('&');
i += 5;
}
else if (str.compare(i, 4, "&lt;") == 0)
{
ret.push_back('<');
i += 4;
}
else if (str.compare(i, 4, "&gt;") == 0)
{
ret.push_back('>');
i += 4;
}
else if (str.compare(i, 6, "&apos;") == 0)
{
ret.push_back('\'');
i += 6;
}
else if (str.compare(i, 6, "&quot;") == 0)
{
ret.push_back('"');
i += 6;
}
else
{
ret.push_back(str[i]);
i++;
}
}
return ret;
}
// Print method for OperationDetailStatus.
std::ostream& operator<<(std::ostream& out, const OperationDetailStatus od_status)
{
switch (od_status)
{
case STATUS_NONE: out << "NONE"; break;
case STATUS_EXECUTE: out << "EXECUTE"; break;
case STATUS_SUCCESS: out << "SUCCESS"; break;
case STATUS_ERROR: out << "ERROR"; break;
case STATUS_INFO: out << "INFO"; break;
case STATUS_WARNING: out << "WARNING"; break;
default: break;
}
return out;
}
// Print method for an OperationDetail object.
std::ostream& operator<<(std::ostream& out, const OperationDetail& od)
{
out << strip_markup(od.get_description());
Glib::ustring elapsed = od.get_elapsed_time();
if (! elapsed.empty())
out << " " << elapsed;
if (od.get_status() != STATUS_NONE)
out << " (" << od.get_status() << ")";
out << "\n";
for (size_t i = 0; i < od.get_childs().size(); i++)
{
out << *od.get_childs()[i];
}
return out;
}
// Explicit test fixture class for common variables and methods used in each test. // Explicit test fixture class for common variables and methods used in each test.
// Reference: // Reference:
// Google Test, Primer, Test Fixtures: Using the Same Data Configuration for Multiple Tests // Google Test, Primer, Test Fixtures: Using the Same Data Configuration for Multiple Tests
@ -226,42 +131,6 @@ const char* first_non_zero_byte(const char* buf, size_t size)
} }
// Number of bytes of binary data to report.
const size_t BinaryStringChunkSize = 16;
// Format up to BinaryStringChunkSize (16) bytes of binary data ready for printing as:
// Hex offset ASCII text Hex bytes
// "0x000000000 \"ABCDEFGHabcdefgh\" 41 42 43 44 45 46 47 48 61 62 63 64 65 66 67 68"
std::string binary_string_to_print(size_t offset, const char* s, size_t len)
{
std::ostringstream result;
result << "0x";
result.fill('0');
result << std::setw(8) << std::hex << std::uppercase << offset << " \"";
size_t i;
for (i = 0; i < BinaryStringChunkSize && i < len; i++)
result.put((isprint(s[i])) ? s[i] : '.');
result.put('\"');
if (len > 0)
{
for (; i < BinaryStringChunkSize; i++)
result.put(' ');
result.put(' ');
for (i = 0 ; i < BinaryStringChunkSize && i < len; i++)
result << " "
<< std::setw(2) << std::hex << std::uppercase
<< (unsigned int)(unsigned char)s[i];
}
return result.str();
}
bool EraseFileSystemSignaturesTest::image_contains_all_zeros() bool EraseFileSystemSignaturesTest::image_contains_all_zeros()
{ {
int fd = open(s_image_name, O_RDONLY|O_NONBLOCK); int fd = open(s_image_name, O_RDONLY|O_NONBLOCK);
@ -329,38 +198,6 @@ TEST_F(EraseFileSystemSignaturesTest, IntelSoftwareRAIDUnaligned)
} // namespace GParted } // namespace GParted
// Re-execute current executable using xvfb-run so that it provides a virtual X11 display.
void exec_using_xvfb_run(int argc, char** argv)
{
// argc+2 = Space for "xvfb-run" command, existing argc strings plus NULL pointer.
size_t size = sizeof(char*) * (argc+2);
char** new_argv = (char**)malloc(size);
if (new_argv == NULL)
{
fprintf(stderr, "Failed to allocate %lu bytes of memory. errno=%d,%s\n",
(unsigned long)size, errno, strerror(errno));
exit(EXIT_FAILURE);
}
new_argv[0] = strdup("xvfb-run");
if (new_argv[0] == NULL)
{
fprintf(stderr, "Failed to allocate %lu bytes of memory. errno=%d,%s\n",
(unsigned long)strlen(new_argv[0])+1, errno, strerror(errno));
exit(EXIT_FAILURE);
}
// Copy argv pointers including final NULL pointer.
for (unsigned int i = 0; i <= (unsigned)argc; i++)
new_argv[i+1] = argv[i];
execvp(new_argv[0], new_argv);
fprintf(stderr, "Failed to execute '%s %s ...'. errno=%d,%s\n", new_argv[0], new_argv[1],
errno, strerror(errno));
exit(EXIT_FAILURE);
}
// Custom Google Test main(). // Custom Google Test main().
// Reference: // Reference:
// * Google Test, Primer, Writing the main() function // * Google Test, Primer, Writing the main() function
@ -368,14 +205,7 @@ void exec_using_xvfb_run(int argc, char** argv)
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
printf("Running main() from %s\n", __FILE__); printf("Running main() from %s\n", __FILE__);
GParted::ensure_x11_display(argc, argv);
const char* display = getenv("DISPLAY");
if (display == NULL)
{
printf("DISPLAY environment variable unset. Executing 'xvfb-run %s ...'\n", argv[0]);
exec_using_xvfb_run(argc, argv);
}
printf("DISPLAY=\"%s\"\n", display);
// Initialise threading in GParted to successfully use Utils:: and // Initialise threading in GParted to successfully use Utils:: and
// FileSystem::execute_command(). Must be before InitGoogleTest(). // FileSystem::execute_command(). Must be before InitGoogleTest().

View File

@ -22,6 +22,7 @@
* being tested. * being tested.
*/ */
#include "common.h"
#include "PipeCapture.h" #include "PipeCapture.h"
#include "gtest/gtest.h" #include "gtest/gtest.h"
@ -48,39 +49,6 @@ static std::string repeat( const std::string & str, size_t count )
return result; return result;
} }
// Number of bytes of binary data to compare and report.
const size_t BinaryStringDiffSize = 16;
// Format up to 16 bytes of binary data ready for printing as:
// Hex offset ASCII text Hex bytes
// "0x000000000 \"ABCDEFGHabcdefgh\" 41 42 43 44 45 46 47 48 61 62 63 64 65 66 67 68"
std::string BinaryStringToPrint( size_t offset, const char * s, size_t len )
{
std::ostringstream result;
result << "0x";
result.fill( '0' );
result << std::setw( 8 ) << std::hex << std::uppercase << offset << " \"";
size_t i;
for ( i = 0 ; i < BinaryStringDiffSize && i < len ; i ++ )
result.put( ( isprint( s[i] ) ) ? s[i] : '.' );
result.put( '\"' );
if ( len > 0 )
{
for ( ; i < BinaryStringDiffSize ; i ++ )
result.put( ' ' );
result.put( ' ' );
for ( i = 0 ; i < BinaryStringDiffSize && i < len ; i ++ )
result << " "
<< std::setw( 2 ) << std::hex << std::uppercase
<< (unsigned int)(unsigned char)s[i];
}
return result.str();
}
// Helper to construct and return message for equality assertion of C++ strings containing // Helper to construct and return message for equality assertion of C++ strings containing
// binary data used in: // binary data used in:
@ -97,10 +65,10 @@ std::string BinaryStringToPrint( size_t offset, const char * s, size_t len )
size_t len2 = rhs.length(); size_t len2 = rhs.length();
while ( len1 > 0 || len2 > 0 ) while ( len1 > 0 || len2 > 0 )
{ {
size_t cmp_span = BinaryStringDiffSize; size_t cmp_span = BinaryStringChunkSize;
cmp_span = ( len1 < cmp_span ) ? len1 : cmp_span; cmp_span = ( len1 < cmp_span ) ? len1 : cmp_span;
cmp_span = ( len2 < cmp_span ) ? len2 : cmp_span; cmp_span = ( len2 < cmp_span ) ? len2 : cmp_span;
if ( cmp_span < BinaryStringDiffSize && len1 != len2 ) if (cmp_span < BinaryStringChunkSize && len1 != len2)
{ {
diff = true; diff = true;
break; break;
@ -127,9 +95,9 @@ std::string BinaryStringToPrint( size_t offset, const char * s, size_t len )
<< "To be equal to: " << rhs_expr << "\n" << "To be equal to: " << rhs_expr << "\n"
<< " Of length: " << rhs.length() << "\n" << " Of length: " << rhs.length() << "\n"
<< "With first binary difference:\n" << "With first binary difference:\n"
<< "< " << BinaryStringToPrint( offset, p1, len1 ) << "\n" << "< " << binary_string_to_print(offset, p1, len1) << "\n"
<< "--\n" << "--\n"
<< "> " << BinaryStringToPrint( offset, p2, len2 ); << "> " << binary_string_to_print(offset, p2, len2);
} }
} }

View File

@ -33,6 +33,8 @@
*/ */
#include "common.h"
#include "insertion_operators.h"
#include "GParted_Core.h" #include "GParted_Core.h"
#include "FileSystem.h" #include "FileSystem.h"
#include "OperationDetail.h" #include "OperationDetail.h"
@ -62,60 +64,6 @@ namespace GParted
{ {
// Hacky XML parser which strips italic and bold markup added in
// OperationDetail::set_description() and reverts just these 5 characters &<>'" encoded by
// Glib::Markup::escape_text() -> g_markup_escape_text() -> append_escaped_text().
Glib::ustring strip_markup(const Glib::ustring& str)
{
size_t len = str.length();
size_t i = 0;
Glib::ustring ret;
ret.reserve(len);
while (i < len)
{
if (str.compare(i, 3, "<i>") == 0)
i += 3;
else if (str.compare(i, 4, "</i>") == 0)
i += 4;
else if (str.compare(i, 3, "<b>") == 0)
i += 3;
else if (str.compare(i, 4, "</b>") == 0)
i += 4;
else if (str.compare(i, 5, "&amp;") == 0)
{
ret.push_back('&');
i += 5;
}
else if (str.compare(i, 4, "&lt;") == 0)
{
ret.push_back('<');
i += 4;
}
else if (str.compare(i, 4, "&gt;") == 0)
{
ret.push_back('>');
i += 4;
}
else if (str.compare(i, 6, "&apos;") == 0)
{
ret.push_back('\'');
i += 6;
}
else if (str.compare(i, 6, "&quot;") == 0)
{
ret.push_back('"');
i += 6;
}
else
{
ret.push_back(str[i]);
i++;
}
}
return ret;
}
// Print method for the messages in a Partition object. // Print method for the messages in a Partition object.
std::ostream& operator<<(std::ostream& out, const Partition& partition) std::ostream& operator<<(std::ostream& out, const Partition& partition)
{ {
@ -127,42 +75,6 @@ std::ostream& operator<<(std::ostream& out, const Partition& partition)
} }
// Print method for OperationDetailStatus.
std::ostream& operator<<(std::ostream& out, const OperationDetailStatus od_status)
{
switch (od_status)
{
case STATUS_NONE: out << "NONE"; break;
case STATUS_EXECUTE: out << "EXECUTE"; break;
case STATUS_SUCCESS: out << "SUCCESS"; break;
case STATUS_ERROR: out << "ERROR"; break;
case STATUS_INFO: out << "INFO"; break;
case STATUS_WARNING: out << "WARNING"; break;
default: break;
}
return out;
}
// Print method for an OperationDetail object.
std::ostream& operator<<(std::ostream& out, const OperationDetail& od)
{
out << strip_markup(od.get_description());
Glib::ustring elapsed = od.get_elapsed_time();
if (! elapsed.empty())
out << " " << elapsed;
if (od.get_status() != STATUS_NONE)
out << " (" << od.get_status() << ")";
out << "\n";
for (unsigned int i = 0; i < od.get_childs().size(); i++)
{
out << *od.get_childs()[i];
}
return out;
}
// Printable file system type which meets the requirements for a Google Test name. // Printable file system type which meets the requirements for a Google Test name.
// Use GParted's file system names except when they contains any non-alphabetic chars. // Use GParted's file system names except when they contains any non-alphabetic chars.
// Reference: // Reference:
@ -724,38 +636,6 @@ INSTANTIATE_TEST_CASE_P(My,
} // namespace GParted } // namespace GParted
// Re-execute current executable using xvfb-run so that it provides a virtual X11 display.
void exec_using_xvfb_run(int argc, char** argv)
{
// argc+2 = Space for "xvfb-run" command, existing argc strings plus NULL pointer.
size_t size = sizeof(char*) * (argc+2);
char** new_argv = (char**)malloc(size);
if (new_argv == NULL)
{
fprintf(stderr, "Failed to allocate %lu bytes of memory. errno=%d,%s\n",
(unsigned long)size, errno, strerror(errno));
exit(EXIT_FAILURE);
}
new_argv[0] = strdup("xvfb-run");
if (new_argv[0] == NULL)
{
fprintf(stderr, "Failed to allocate %lu bytes of memory. errno=%d,%s\n",
(unsigned long)strlen(new_argv[0])+1, errno, strerror(errno));
exit(EXIT_FAILURE);
}
// Copy argv pointers including final NULL pointer.
for (unsigned int i = 0; i <= (unsigned)argc; i++)
new_argv[i+1] = argv[i];
execvp(new_argv[0], new_argv);
fprintf(stderr, "Failed to execute '%s %s ...'. errno=%d,%s\n", new_argv[0], new_argv[1],
errno, strerror(errno));
exit(EXIT_FAILURE);
}
// Custom Google Test main(). // Custom Google Test main().
// Reference: // Reference:
// * Google Test, Primer, Writing the main() function // * Google Test, Primer, Writing the main() function
@ -763,14 +643,7 @@ void exec_using_xvfb_run(int argc, char** argv)
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
printf("Running main() from %s\n", __FILE__); printf("Running main() from %s\n", __FILE__);
GParted::ensure_x11_display(argc, argv);
const char* display = getenv("DISPLAY");
if (display == NULL)
{
printf("DISPLAY environment variable unset. Executing 'xvfb-run %s ...'\n", argv[0]);
exec_using_xvfb_run(argc, argv);
}
printf("DISPLAY=\"%s\"\n", display);
// Initialise threading in GParted to allow FileSystem interface classes to // Initialise threading in GParted to allow FileSystem interface classes to
// successfully use Utils:: and Filesystem::execute_command(). Must be before // successfully use Utils:: and Filesystem::execute_command(). Must be before