Implement a ttytype test for the FTermDetection unit test

This commit is contained in:
Markus Gans 2018-09-16 19:33:40 +02:00
parent 5543157de5
commit 0029c41bad
11 changed files with 318 additions and 55 deletions

View File

@ -1,3 +1,6 @@
2018-09-16 Markus Gans <guru.mail@muenster.de>
* Implement a ttytype test for the FTermDetection unit test
2018-09-14 Markus Gans <guru.mail@muenster.de>
* Added unit test for FTermDetection with a terminal simulation
for common terminals

View File

@ -152,6 +152,7 @@ class FTermDetection
static void setTmuxTerm (bool);
static void setTerminalDetection (bool);
static void setTermFileName (char[]);
static void setTtyTypeFileName (char[]);
// Methods
static void detect();
@ -166,7 +167,7 @@ class FTermDetection
private:
// Methods
static void getSystemTermType();
static void getTTYtype();
static bool getTTYtype();
#if F_HAVE_GETTTYNAM
static bool getTTYSFileEntry();
#endif
@ -187,6 +188,7 @@ class FTermDetection
static char* secDA_Analysis_1 (char[]);
static char* secDA_Analysis_24 (char[]);
static char* secDA_Analysis_32 (char[]);
static char* secDA_Analysis_67 (char[]);
static char* secDA_Analysis_77 (char[]);
static char* secDA_Analysis_82 (char[]);
static char* secDA_Analysis_83 (char[]);
@ -196,6 +198,7 @@ class FTermDetection
// Data Members
static char termtype[256];
static char termfilename[256];
static char ttytypename[256];
static bool decscusr_support;
static bool terminal_detection;
static bool color256;

View File

@ -508,10 +508,12 @@ inline bool FFileDialog::pattern_match ( const char* const pattern
{
search[0] = '.';
search[1] = '\0';
std::strncat(search, pattern, sizeof(search) - std::strlen(search) - 1);
std::strncat(search, pattern, sizeof(search) - std::strlen(search));
}
else
std::strncpy(search, pattern, sizeof(search) - 1);
std::strncpy(search, pattern, sizeof(search));
search[sizeof(search) - 1] = '\0';
if ( fnmatch (search, fname, FNM_PERIOD) == 0 )
return true;
@ -699,10 +701,12 @@ void FFileDialog::followSymLink (const char* const dir, dir_entry& entry)
char symLink[MAXPATHLEN] = { };
struct stat sb;
std::strncpy (symLink, dir, sizeof(symLink) - 1);
std::strncpy (symLink, dir, sizeof(symLink));
symLink[sizeof(symLink) - 1] = '\0';
std::strncat ( symLink
, entry.name
, sizeof(symLink) - std::strlen(symLink) - 1);
, sizeof(symLink) - std::strlen(symLink));
symLink[sizeof(symLink) - 1] = '\0';
if ( realpath(symLink, resolved_path) == 0 )
return; // Cannot follow the symlink

View File

@ -1694,7 +1694,8 @@ inline bool FOptiAttr::append_sequence (char seq[])
{
if ( seq )
{
std::strncat (attr_ptr, seq, sizeof(attr_buf) - std::strlen(attr_ptr) - 1 );
std::strncat (attr_ptr, seq, sizeof(attr_buf) - std::strlen(attr_ptr));
attr_buf[sizeof(attr_buf) - 1] = '\0';
return true;
}
else

View File

@ -744,9 +744,12 @@ inline int FOptiMove::verticalMove (char move[], int from_y, int to_y)
if ( F_row_address.cap )
{
if ( move )
{
std::strncpy ( move
, tparm(F_row_address.cap, to_y, 0, 0, 0, 0, 0, 0, 0, 0)
, BUF_SIZE - 1 );
, BUF_SIZE );
move[BUF_SIZE - 1] = '\0';
}
vtime = F_row_address.duration;
}
@ -768,9 +771,12 @@ inline void FOptiMove::downMove ( char move[], int& vtime
if ( F_parm_down_cursor.cap && F_parm_down_cursor.duration < vtime )
{
if ( move )
{
std::strncpy ( move
, tparm(F_parm_down_cursor.cap, num, 0, 0, 0, 0, 0, 0, 0, 0)
, BUF_SIZE - 1 );
, BUF_SIZE );
move[BUF_SIZE - 1] = '\0';
}
vtime = F_parm_down_cursor.duration;
}
@ -793,9 +799,12 @@ inline void FOptiMove::upMove ( char move[], int& vtime
if ( F_parm_up_cursor.cap && F_parm_up_cursor.duration < vtime )
{
if ( move )
{
std::strncpy ( move
, tparm(F_parm_up_cursor.cap, num, 0, 0, 0, 0, 0, 0, 0, 0)
, BUF_SIZE - 1 );
, BUF_SIZE );
move[BUF_SIZE - 1] = '\0';
}
vtime = F_parm_up_cursor.duration;
}
@ -819,7 +828,8 @@ inline int FOptiMove::horizontalMove (char hmove[], int from_x, int to_x)
// Move to fixed column position1
std::strncat ( hmove
, tparm(F_column_address.cap, to_x, 0, 0, 0, 0, 0, 0, 0, 0)
, BUF_SIZE - std::strlen(hmove) - 1 );
, BUF_SIZE - std::strlen(hmove) );
hmove[BUF_SIZE - 1] = '\0';
htime = F_column_address.duration;
}
@ -841,7 +851,8 @@ inline void FOptiMove::rightMove ( char hmove[], int& htime
{
std::strncpy ( hmove
, tparm(F_parm_right_cursor.cap, num, 0, 0, 0, 0, 0, 0, 0, 0)
, BUF_SIZE - 1 );
, BUF_SIZE );
hmove[BUF_SIZE - 1] = '\0';
htime = F_parm_right_cursor.duration;
}
@ -895,7 +906,8 @@ inline void FOptiMove::leftMove ( char hmove[], int& htime
{
std::strncpy ( hmove
, tparm(F_parm_left_cursor.cap, num, 0, 0, 0, 0, 0, 0, 0, 0)
, BUF_SIZE - 1 );
, BUF_SIZE );
hmove[BUF_SIZE - 1] = '\0';
htime = F_parm_left_cursor.duration;
}
@ -959,7 +971,8 @@ inline bool FOptiMove::isMethod0Faster ( int& move_time
if ( move_xy )
{
char* move_ptr = move_buf;
std::strncpy (move_ptr, move_xy, BUF_SIZE - 1);
std::strncpy (move_ptr, move_xy, BUF_SIZE);
move_ptr[BUF_SIZE - 1] = '\0';
move_time = F_cursor_address.duration;
return true;
}
@ -1108,22 +1121,25 @@ void FOptiMove::moveByMethod ( int method
case 2:
if ( F_carriage_return.cap )
{
std::strncpy (move_ptr, F_carriage_return.cap, BUF_SIZE - 1);
std::strncpy (move_ptr, F_carriage_return.cap, BUF_SIZE);
move_ptr += F_carriage_return.length;
relativeMove (move_ptr, 0, yold, xnew, ynew);
move_buf[BUF_SIZE - 1] ='\0';
}
break;
case 3:
std::strncpy (move_ptr, F_cursor_home.cap, BUF_SIZE - 1);
std::strncpy (move_ptr, F_cursor_home.cap, BUF_SIZE);
move_ptr += F_cursor_home.length;
relativeMove (move_ptr, 0, 0, xnew, ynew);
move_buf[BUF_SIZE - 1] ='\0';
break;
case 4:
std::strncpy (move_ptr, F_cursor_to_ll.cap, BUF_SIZE - 1);
std::strncpy (move_ptr, F_cursor_to_ll.cap, BUF_SIZE);
move_ptr += F_cursor_to_ll.length;
relativeMove (move_ptr, 0, screen_height - 1, xnew, ynew);
move_buf[BUF_SIZE - 1] ='\0';
break;
case 5:
@ -1132,13 +1148,14 @@ void FOptiMove::moveByMethod ( int method
if ( xold >= 0 )
std::strncat ( move_ptr
, F_carriage_return.cap
, BUF_SIZE - std::strlen(move_ptr) - 1 );
, BUF_SIZE - std::strlen(move_ptr) );
std::strncat ( move_ptr
, F_cursor_left.cap
, BUF_SIZE - std::strlen(move_ptr) - 1 );
, BUF_SIZE - std::strlen(move_ptr) );
move_ptr += std::strlen(move_buf);
relativeMove (move_ptr, screen_width - 1, yold - 1, xnew, ynew);
move_buf[BUF_SIZE - 1] ='\0';
break;
default:

View File

@ -2668,6 +2668,7 @@ inline void FString::_assign (const wchar_t s[])
}
std::wcsncpy (string, s, bufsize);
string[bufsize - 1] = L'\0';
length = new_length;
}
@ -2695,6 +2696,7 @@ inline void FString::_insert (uInt pos, uInt len, const wchar_t s[])
}
std::wcsncpy (string, s, bufsize);
string[bufsize - 1] = L'\0';
return;
}
else

View File

@ -450,9 +450,9 @@ char* FTerm::enableCursor()
char*& ve = TCAP(fc::t_cursor_normal);
if ( ve )
std::strncpy (enable_str, ve, SIZE - 1);
std::strncpy (enable_str, ve, SIZE);
else if ( vs )
std::strncpy (enable_str, vs, SIZE - 1);
std::strncpy (enable_str, vs, SIZE);
#if defined(__linux__)
if ( isLinuxTerm() )
@ -460,10 +460,12 @@ char* FTerm::enableCursor()
// Restore the last used Linux console cursor style
char* cstyle;
cstyle = linux->restoreCursorStyle();
std::strncat (enable_str, cstyle, SIZE - std::strlen(enable_str) - 1);
std::strncat (enable_str, cstyle, SIZE - std::strlen(enable_str));
}
#endif
enable_str[SIZE - 1] = '\0';
#if defined(__FreeBSD__) || defined(__DragonFly__)
if ( isFreeBSDTerm() )
{

View File

@ -46,7 +46,8 @@ FTermcapQuirks::~FTermcapQuirks() // destructor
//----------------------------------------------------------------------
void FTermcapQuirks::setTerminalType (const char tt[])
{
std::strncpy (termtype, tt, sizeof(termtype) - 1);
std::strncpy (termtype, tt, sizeof(termtype));
termtype[sizeof(termtype) - 1] = '\0';
}
//----------------------------------------------------------------------

View File

@ -30,6 +30,7 @@ FTermDetection::colorEnv FTermDetection::color_env;
FTermDetection::secondaryDA FTermDetection::secondary_da;
char FTermDetection::termtype[256] = { };
char FTermDetection::termfilename[256] = { };
char FTermDetection::ttytypename[256] = { };
bool FTermDetection::decscusr_support;
bool FTermDetection::terminal_detection;
bool FTermDetection::color256;
@ -66,6 +67,10 @@ FTermDetection::FTermDetection()
// Initialize the structs
color_env.setDefault();
secondary_da.setDefault();
// Set default ttytype file
std::strncpy (ttytypename, C_STR("/etc/ttytype"), sizeof(ttytypename));
ttytypename[sizeof(ttytypename) - 1] = '\0';
}
//----------------------------------------------------------------------
@ -86,7 +91,18 @@ void FTermDetection::setTermFileName (char term_filename[])
if ( ! term_filename )
return;
std::strncpy (termfilename, term_filename, sizeof(termfilename) - 1);
std::strncpy (termfilename, term_filename, sizeof(termfilename));
termfilename[sizeof(termfilename) - 1] = '\0';
}
//----------------------------------------------------------------------
void FTermDetection::setTtyTypeFileName (char ttytype_filename[])
{
if ( ! ttytype_filename )
return;
std::strncpy (ttytypename, ttytype_filename, sizeof(ttytypename));
ttytypename[sizeof(ttytypename) - 1] = '\0';
}
//----------------------------------------------------------------------
@ -113,12 +129,14 @@ void FTermDetection::getSystemTermType()
if ( term_env )
{
// Save name in termtype
std::strncpy (termtype, term_env, sizeof(termtype) - 1);
std::strncpy (termtype, term_env, sizeof(termtype));
termtype[sizeof(termtype) - 1] = '\0';
return;
}
else if ( *termfilename ) // 1st fallback: use the teminal file name
{
getTTYtype(); // Look into /etc/ttytype
if ( getTTYtype() ) // Look into /etc/ttytype
return;
#if F_HAVE_GETTTYNAM
if ( getTTYSFileEntry() ) // Look into /etc/ttys
@ -131,7 +149,7 @@ void FTermDetection::getSystemTermType()
}
//----------------------------------------------------------------------
void FTermDetection::getTTYtype()
bool FTermDetection::getTTYtype()
{
// Analyse /etc/ttytype and get the term name
// ------------------------------------------
@ -152,7 +170,7 @@ void FTermDetection::getTTYtype()
std::FILE *fp;
if ( (fp = std::fopen("/etc/ttytype", "r")) != 0 )
if ( (fp = std::fopen(ttytypename, "r")) != 0 )
{
char* p;
char str[BUFSIZ];
@ -180,14 +198,17 @@ void FTermDetection::getTTYtype()
if ( type != 0 && name != 0 && ! std::strcmp(name, term_basename) )
{
// Save name in termtype
std::strncpy (termtype, type, sizeof(termtype) - 1);
std::strncpy (termtype, type, sizeof(termtype));
termtype[sizeof(termtype) - 1] = '\0';
std::fclose(fp);
return;
return true;
}
}
std::fclose(fp);
}
return false;
}
#if F_HAVE_GETTTYNAM
@ -214,7 +235,8 @@ bool FTermDetection::getTTYSFileEntry()
if ( type != 0 )
{
// Save name in termtype
std::strncpy (termtype, type, sizeof(termtype) - 1);
std::strncpy (termtype, type, sizeof(termtype));
termtype[sizeof(termtype) - 1] = '\0';
endttyent();
return true;
}
@ -326,7 +348,8 @@ void FTermDetection::detectTerminal()
if ( new_termtype )
{
setenv(C_STR("TERM"), new_termtype, 1);
std::strncpy (termtype, new_termtype, sizeof(termtype) - 1);
std::strncpy (termtype, new_termtype, sizeof(termtype));
termtype[sizeof(termtype) - 1] = '\0';
}
}
@ -723,6 +746,7 @@ char* FTermDetection::secDA_Analysis (char current_termtype[])
case 64: // DEC VT520
case 65: // DEC VT525
case 67: // Cygwin
new_termtype = secDA_Analysis_67(current_termtype);
break;
case 77: // mintty
@ -840,6 +864,18 @@ inline char* FTermDetection::secDA_Analysis_32 (char[])
return new_termtype;
}
//----------------------------------------------------------------------
inline char* FTermDetection::secDA_Analysis_67 (char[])
{
// Terminal ID 67 - cygwin
char* new_termtype;
terminal_type.cygwin = true;
new_termtype = C_STR("cygwin");
std::fflush(stdout);
return new_termtype;
}
//----------------------------------------------------------------------
inline char* FTermDetection::secDA_Analysis_77 (char[])
{

View File

@ -32,6 +32,8 @@
#include <sys/wait.h>
#include <sys/mman.h>
#define CPPUNIT_ASSERT_CSTRING(expected, actual) \
check_c_string (expected, actual, CPPUNIT_SOURCELINE())
static char* colorname[] =
{
@ -294,6 +296,20 @@ static char* colorname[] =
0
};
//----------------------------------------------------------------------
void check_c_string ( const char* s1
, const char* s2
, CppUnit::SourceLine sourceLine )
{
if ( s1 == 0 && s2 == 0 ) // Strings are equal
return;
if ( s1 && s2 && std::strcmp (s1, s2) == 0 ) // Strings are equal
return;
::CppUnit::Asserter::fail ("Strings are not equal", sourceLine);
}
//----------------------------------------------------------------------
// class FTermDetectionTest
@ -353,6 +369,7 @@ class FTermDetectionTest : public CPPUNIT_NS::TestFixture
void sunTest();
void screenTest();
void tmuxTest();
void ttytypeTest();
private:
char* getAnswerback (console);
@ -396,6 +413,7 @@ class FTermDetectionTest : public CPPUNIT_NS::TestFixture
CPPUNIT_TEST (sunTest);
CPPUNIT_TEST (screenTest);
CPPUNIT_TEST (tmuxTest);
CPPUNIT_TEST (ttytypeTest);
// End of test suite definition
CPPUNIT_TEST_SUITE_END();
@ -464,6 +482,7 @@ void FTermDetectionTest::ansiTest()
if ( isChildProcess(pid) )
{
setenv ("TERM", "ansi", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
@ -495,6 +514,14 @@ void FTermDetectionTest::ansiTest()
CPPUNIT_ASSERT ( ! detect.canDisplay256Colors() );
CPPUNIT_ASSERT ( ! detect.hasTerminalDetection() );
CPPUNIT_ASSERT ( ! detect.hasSetCursorStyleSupport() );
CPPUNIT_ASSERT_CSTRING ( detect.getTermType(), C_STR("ansi") );
// Test fallback to vt100 without TERM environment variable
unsetenv("TERM");
detect.setAnsiTerminal(false);
detect.detect();
CPPUNIT_ASSERT ( ! detect.isAnsiTerminal() );
CPPUNIT_ASSERT_CSTRING ( detect.getTermType(), C_STR("vt100") );
debugOutput();
closeStandardStreams();
@ -506,7 +533,7 @@ void FTermDetectionTest::ansiTest()
terminalSimulation (ansi);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -523,6 +550,7 @@ void FTermDetectionTest::xtermTest()
{
setenv ("TERM", "xterm", 1);
setenv ("XTERM_VERSION", "XTerm(312)", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("ROXTERM_ID");
@ -564,7 +592,7 @@ void FTermDetectionTest::xtermTest()
terminalSimulation (xterm);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -581,6 +609,7 @@ void FTermDetectionTest::rxvtTest()
{
setenv ("TERM", "rxvt-cygwin-native", 1);
setenv ("COLORTERM", "rxvt-xpm", 1);
unsetenv("TERMCAP");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
unsetenv("ROXTERM_ID");
@ -622,7 +651,7 @@ void FTermDetectionTest::rxvtTest()
terminalSimulation (rxvt);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -639,6 +668,7 @@ void FTermDetectionTest::urxvtTest()
{
setenv ("TERM", "rxvt-unicode-256color", 1);
setenv ("COLORTERM", "rxvt-xpm", 1);
unsetenv("TERMCAP");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
unsetenv("ROXTERM_ID");
@ -680,7 +710,7 @@ void FTermDetectionTest::urxvtTest()
terminalSimulation (urxvt);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -697,6 +727,7 @@ void FTermDetectionTest::mltermTest()
{
setenv ("TERM", "mlterm", 1);
setenv ("MLTERM", "3.8.4", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
@ -739,7 +770,7 @@ void FTermDetectionTest::mltermTest()
terminalSimulation (mlterm);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -755,6 +786,7 @@ void FTermDetectionTest::puttyTest()
if ( isChildProcess(pid) )
{
setenv ("TERM", "xterm", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
@ -798,7 +830,7 @@ void FTermDetectionTest::puttyTest()
terminalSimulation (putty);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -817,6 +849,7 @@ void FTermDetectionTest::kdeKonsoleTest()
setenv ("COLORTERM", "truecolor", 1);
setenv ("KONSOLE_DBUS_SERVICE", "DCOPRef(konsole-11768,konsole)", 1);
setenv ("KONSOLE_DCOP", ":1.77", 1);
unsetenv("TERMCAP");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
unsetenv("ROXTERM_ID");
@ -856,7 +889,7 @@ void FTermDetectionTest::kdeKonsoleTest()
terminalSimulation (kde_konsole);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -874,6 +907,7 @@ void FTermDetectionTest::gnomeTerminalTest()
setenv ("TERM", "xterm-256color", 1);
setenv ("COLORTERM", "truecolor", 1);
setenv ("VTE_VERSION", "5202", 1);
unsetenv("TERMCAP");
unsetenv("XTERM_VERSION");
unsetenv("ROXTERM_ID");
unsetenv("KONSOLE_DBUS_SESSION");
@ -915,7 +949,7 @@ void FTermDetectionTest::gnomeTerminalTest()
terminalSimulation (gnome_terminal);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -931,6 +965,7 @@ void FTermDetectionTest::ktermTest()
if ( isChildProcess(pid) )
{
setenv ("TERM", "kterm", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
@ -964,6 +999,13 @@ void FTermDetectionTest::ktermTest()
CPPUNIT_ASSERT ( ! detect.hasTerminalDetection() );
CPPUNIT_ASSERT ( ! detect.hasSetCursorStyleSupport() );
// Test fallback to vt100 without TERM environment variable
unsetenv("TERM");
detect.setKtermTerminal(false);
detect.detect();
CPPUNIT_ASSERT ( ! detect.isKtermTerminal() );
CPPUNIT_ASSERT_CSTRING ( detect.getTermType(), C_STR("vt100") );
debugOutput();
closeStandardStreams();
exit(EXIT_SUCCESS);
@ -974,7 +1016,7 @@ void FTermDetectionTest::ktermTest()
terminalSimulation (kterm);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -990,6 +1032,7 @@ void FTermDetectionTest::teraTermTest()
if ( isChildProcess(pid) )
{
setenv ("TERM", "xterm", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
@ -1033,7 +1076,7 @@ void FTermDetectionTest::teraTermTest()
terminalSimulation (tera_term);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -1049,6 +1092,7 @@ void FTermDetectionTest::cygwinTest()
if ( isChildProcess(pid) )
{
setenv ("TERM", "cygwin", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
@ -1092,7 +1136,7 @@ void FTermDetectionTest::cygwinTest()
terminalSimulation (cygwin);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -1108,6 +1152,7 @@ void FTermDetectionTest::minttyTest()
if ( isChildProcess(pid) )
{
setenv ("TERM", "xterm-256color", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
@ -1151,7 +1196,7 @@ void FTermDetectionTest::minttyTest()
terminalSimulation (mintty);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -1167,6 +1212,7 @@ void FTermDetectionTest::linuxTest()
if ( isChildProcess(pid) )
{
setenv ("TERM", "linux", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
@ -1200,6 +1246,13 @@ void FTermDetectionTest::linuxTest()
CPPUNIT_ASSERT ( detect.hasTerminalDetection() );
CPPUNIT_ASSERT ( ! detect.hasSetCursorStyleSupport() );
// Test fallback to vt100 without TERM environment variable
unsetenv("TERM");
detect.setLinuxTerm(false);
detect.detect();
CPPUNIT_ASSERT ( ! detect.isLinuxTerm() );
CPPUNIT_ASSERT_CSTRING ( detect.getTermType(), C_STR("vt100") );
debugOutput();
closeStandardStreams();
exit(EXIT_SUCCESS);
@ -1210,7 +1263,7 @@ void FTermDetectionTest::linuxTest()
terminalSimulation (linux_con);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -1226,6 +1279,7 @@ void FTermDetectionTest::freebsdTest()
if ( isChildProcess(pid) )
{
setenv ("TERM", "xterm", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
@ -1260,6 +1314,15 @@ void FTermDetectionTest::freebsdTest()
CPPUNIT_ASSERT ( detect.hasTerminalDetection() );
CPPUNIT_ASSERT ( ! detect.hasSetCursorStyleSupport() );
// Test fallback to vt100 without TERM environment variable
unsetenv("TERM");
detect.setXTerminal (false);
detect.setFreeBSDTerm(false);
detect.detect();
CPPUNIT_ASSERT ( ! detect.isXTerminal() );
CPPUNIT_ASSERT ( ! detect.isFreeBSDTerm() );
CPPUNIT_ASSERT_CSTRING ( detect.getTermType(), C_STR("vt100") );
debugOutput();
closeStandardStreams();
exit(EXIT_SUCCESS);
@ -1270,7 +1333,7 @@ void FTermDetectionTest::freebsdTest()
terminalSimulation (freebsd_con);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -1286,6 +1349,7 @@ void FTermDetectionTest::netbsdTest()
if ( isChildProcess(pid) )
{
setenv ("TERM", "wsvt25", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
@ -1320,6 +1384,13 @@ void FTermDetectionTest::netbsdTest()
CPPUNIT_ASSERT ( detect.hasTerminalDetection() );
CPPUNIT_ASSERT ( ! detect.hasSetCursorStyleSupport() );
// Test fallback to vt100 without TERM environment variable
unsetenv("TERM");
detect.setNetBSDTerm(false);
detect.detect();
CPPUNIT_ASSERT ( ! detect.isFreeBSDTerm() );
CPPUNIT_ASSERT_CSTRING ( detect.getTermType(), C_STR("vt100") );
debugOutput();
closeStandardStreams();
exit(EXIT_SUCCESS);
@ -1330,7 +1401,7 @@ void FTermDetectionTest::netbsdTest()
terminalSimulation (netbsd_con);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -1346,6 +1417,7 @@ void FTermDetectionTest::openbsdTest()
if ( isChildProcess(pid) )
{
setenv ("TERM", "vt220", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
@ -1380,6 +1452,13 @@ void FTermDetectionTest::openbsdTest()
CPPUNIT_ASSERT ( detect.hasTerminalDetection() );
CPPUNIT_ASSERT ( ! detect.hasSetCursorStyleSupport() );
// Test fallback to vt100 without TERM environment variable
unsetenv("TERM");
detect.setOpenBSDTerm(false);
detect.detect();
CPPUNIT_ASSERT ( ! detect.isOpenBSDTerm() );
CPPUNIT_ASSERT_CSTRING ( detect.getTermType(), C_STR("vt100") );
debugOutput();
closeStandardStreams();
exit(EXIT_SUCCESS);
@ -1390,7 +1469,7 @@ void FTermDetectionTest::openbsdTest()
terminalSimulation (openbsd_con);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -1405,6 +1484,7 @@ void FTermDetectionTest::sunTest()
if ( isChildProcess(pid) )
{
setenv ("TERM", "sun-color", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
@ -1438,6 +1518,13 @@ void FTermDetectionTest::sunTest()
CPPUNIT_ASSERT ( ! detect.hasTerminalDetection() );
CPPUNIT_ASSERT ( ! detect.hasSetCursorStyleSupport() );
// Test fallback to vt100 without TERM environment variable
unsetenv("TERM");
detect.setSunTerminal(false);
detect.detect();
CPPUNIT_ASSERT ( ! detect.isSunTerminal() );
CPPUNIT_ASSERT_CSTRING ( detect.getTermType(), C_STR("vt100") );
debugOutput();
closeStandardStreams();
exit(EXIT_SUCCESS);
@ -1448,7 +1535,7 @@ void FTermDetectionTest::sunTest()
terminalSimulation (sun_con);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -1508,7 +1595,7 @@ void FTermDetectionTest::screenTest()
terminalSimulation (screen);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
@ -1526,6 +1613,7 @@ void FTermDetectionTest::tmuxTest()
setenv ("TERM", "screen", 1);
setenv ("TMUX", "/tmp/tmux-1000/default,7844,0", 1);
setenv ("TMUX_PANE", "%0", 1);
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
@ -1568,10 +1656,99 @@ void FTermDetectionTest::tmuxTest()
terminalSimulation (tmux);
if ( waitpid(pid, 0, 0) != pid )
::fprintf (stderr, "waitpid error");
std::cerr << "waitpid error" << std::endl;
}
}
//----------------------------------------------------------------------
void FTermDetectionTest::ttytypeTest()
{
struct stat sb = { };
if ( stat("new-root-dir", &sb) == -1 )
if ( mkdir("new-root-dir", 0755) == -1 )
return;
if ( stat("new-root-dir/etc", &sb) == -1 )
if ( mkdir("new-root-dir/etc", 0755) == -1 )
return;
// Write a own /etc/ttytype file
std::ofstream ttytype ("new-root-dir/etc/ttytype");
if ( ! ttytype.is_open() )
{
rmdir("new-root-dir/etc");
rmdir("new-root-dir");
return;
}
ttytype << "linux" << "\t" << "tty1" << std::endl;
ttytype << "linux" << "\t" << "tty2" << std::endl;
ttytype << "linux" << "\t" << "tty3" << std::endl;
ttytype << "linux" << "\t" << "tty4" << std::endl;
ttytype << "linux" << "\t" << "tty5" << std::endl;
ttytype << "linux" << "\t" << "tty6" << std::endl;
ttytype << "vt100" << "\t" << "ttyp0" << std::endl;
ttytype << "vt100" << "\t" << "ttyp1" << std::endl;
ttytype << "vt100" << "\t" << "ttyp2" << std::endl;
ttytype << "vt100" << "\t" << "ttyp3" << std::endl;
ttytype << "vt100" << "\t" << "ttyp4" << std::endl;
ttytype << "vt100" << "\t" << "ttyp5" << std::endl;
ttytype << "vt100" << "\t" << "ttyp6" << std::endl;
ttytype.close();
FTermDetection detect;
detect.setTerminalDetection(true);
detect.setTtyTypeFileName(C_STR("new-root-dir/etc/ttytype"));
pid_t pid = forkProcess();
if ( isChildProcess(pid) )
{
unsetenv("TERM");
unsetenv("TERMCAP");
unsetenv("COLORTERM");
unsetenv("VTE_VERSION");
unsetenv("XTERM_VERSION");
unsetenv("ROXTERM_ID");
unsetenv("KONSOLE_DBUS_SESSION");
unsetenv("KONSOLE_DCOP");
unsetenv("TMUX");
// Test /dev/tty3 with linux
detect.setTermFileName(C_STR("/dev/tty3"));
detect.detect();
CPPUNIT_ASSERT_CSTRING ( detect.getTermType(), C_STR("linux") );
// Test /dev/ttyp0 with vt100
detect.setTermFileName(C_STR("/dev/ttyp0"));
detect.detect();
CPPUNIT_ASSERT_CSTRING ( detect.getTermType(), C_STR("vt100") );
// Test non-existent /dev/tty8 with fallback to vt100
detect.setTermFileName(C_STR("/dev/tty8"));
detect.detect();
CPPUNIT_ASSERT_CSTRING ( detect.getTermType(), C_STR("vt100") );
debugOutput();
closeStandardStreams();
exit(EXIT_SUCCESS);
}
else // Parent
{
// Start the terminal simulation
terminalSimulation (ansi);
if ( waitpid(pid, 0, 0) != pid )
std::cerr << "waitpid error" << std::endl;
}
unlink("new-root-dir/etc/ttytype");
rmdir("new-root-dir/etc");
rmdir("new-root-dir");
}
// private methods of FOptiMoveTest
//----------------------------------------------------------------------
@ -1770,9 +1947,9 @@ void FTermDetectionTest::debugOutput()
setenv ("GO_RIGHT", "\\033[79D\\033[40C", 1);
FString line (69, '-');
::printf ("\n%s\n", line.c_str());
::printf ("Probe Escape sequence Reply\n");
::printf ("%s\n", line.c_str());
std::cout << std::endl << line << std::endl;
std::cout << "Probe Escape sequence Reply";
std::cout << std::endl << line << std::endl;
// Command line
char* child_av[] =
@ -1900,7 +2077,10 @@ pid_t FTermDetectionTest::forkProcess()
#ifdef TIOCSCTTY
// Set controlling tty
if ( ioctl(fd_slave, TIOCSCTTY, 0) == -1 )
{
*shared_state = true;
return -1;
}
#endif
// Get current terminal settings
@ -1909,6 +2089,20 @@ pid_t FTermDetectionTest::forkProcess()
// Set raw mode on the slave side of the PTY
cfmakeraw (&term_settings);
tcsetattr (fd_slave, TCSANOW, &term_settings);
#ifdef TIOCSWINSZ
// Set slave tty window size
struct winsize size;
size.ws_row = 25;
size.ws_col = 80;
if ( ioctl(fd_slave, TIOCSWINSZ, &size) == -1)
{
*shared_state = true;
return -1;
}
#endif
closeStandardStreams();
fd_stdin = dup(fd_slave); // PTY becomes stdin (0)