make fish_tests work on MS Windows with C++11

On Cygwin there are two narrowing conversions at line 931 in
src/fish_tests.cpp due to the code assuming a wchar_t is four bytes.
Obviously that's wrong but only became an issue with the pending change to
switch to C++11. The problematic values aren't actually used on Windows
because the tests that would use them are bypassed if is_wchar_ucs2()
returns true. This change predicates that code on a compile time rather
than a run time test.
This commit is contained in:
Kurtis Rader 2016-11-20 18:05:34 -08:00
parent b16511344e
commit b8778ba4a2

View file

@ -11,6 +11,7 @@
#include <stdarg.h>
#include <stddef.h>
#include <stdio.h>
#include <stdint.h>
#include <stdlib.h>
#include <string.h>
#include <sys/select.h>
@ -928,10 +929,7 @@ static void test_utf8() {
wchar_t w1[] = {0x54, 0x65, 0x73, 0x74};
wchar_t w2[] = {0x0422, 0x0435, 0x0441, 0x0442};
wchar_t w3[] = {0x800, 0x1e80, 0x98c4, 0x9910, 0xff00};
wchar_t w4[] = {0x15555, 0xf7777, 0x0a};
wchar_t wb[] = {(wchar_t)-2, 0xa, (wchar_t)0xffffffff, 0x0441};
wchar_t wm[] = {0x41, 0x0441, 0x3042, 0xff67, 0x9b0d};
wchar_t wb1[] = {0x0a, 0x0422};
wchar_t wb2[] = {0xd800, 0xda00, 0x41, 0xdfff, 0x0a};
wchar_t wbom[] = {0xfeff, 0x41, 0x0a};
wchar_t wbom2[] = {0x41, 0xa};
@ -940,14 +938,19 @@ static void test_utf8() {
unsigned char u2[] = {0xd0, 0xa2, 0xd0, 0xb5, 0xd1, 0x81, 0xd1, 0x82};
unsigned char u3[] = {0xe0, 0xa0, 0x80, 0xe1, 0xba, 0x80, 0xe9, 0xa3,
0x84, 0xe9, 0xa4, 0x90, 0xef, 0xbc, 0x80};
unsigned char u4[] = {0xf0, 0x95, 0x95, 0x95, 0xf3, 0xb7, 0x9d, 0xb7, 0x0a};
unsigned char ub[] = {0xa, 0xd1, 0x81};
unsigned char um[] = {0x41, 0xd1, 0x81, 0xe3, 0x81, 0x82, 0xef, 0xbd, 0xa7, 0xe9, 0xac, 0x8d};
unsigned char ub1[] = {0xa, 0xff, 0xd0, 0xa2, 0xfe, 0x8f, 0xe0, 0x80};
unsigned char uc080[] = {0xc0, 0x80};
unsigned char ub2[] = {0xed, 0xa1, 0x8c, 0xed, 0xbe, 0xb4, 0x0a};
unsigned char ubom[] = {0x41, 0xa};
unsigned char ubom2[] = {0xef, 0xbb, 0xbf, 0x41, 0x0a};
#if WCHAR_MAX != 0xffff
wchar_t w4[] = {0x15555, 0xf7777, 0x0a};
wchar_t wb[] = {(wchar_t)-2, 0xa, (wchar_t)0xffffffff, 0x0441};
wchar_t wb1[] = {0x0a, 0x0422};
unsigned char u4[] = {0xf0, 0x95, 0x95, 0x95, 0xf3, 0xb7, 0x9d, 0xb7, 0x0a};
unsigned char ub[] = {0xa, 0xd1, 0x81};
unsigned char ub1[] = {0xa, 0xff, 0xd0, 0xa2, 0xfe, 0x8f, 0xe0, 0x80};
#endif
// UTF-8 -> UCS-4 string.
test_utf82wchar(ubom2, sizeof(ubom2), wbom2, sizeof(wbom2) / sizeof(*wbom2), UTF8_SKIP_BOM,
@ -991,18 +994,6 @@ static void test_utf8() {
test_wchar2utf8(w1, sizeof(w1) / sizeof(*w1), u1, 0, 0, 0, "invalid params, dst is not NULL");
test_wchar2utf8(NULL, 10, nullc, 0, 0, 0, "invalid params, src length is not 0");
// The following tests won't pass on systems (e.g., Cygwin) where sizeof wchar_t is 2. That's
// due to several reasons but the primary one is that narrowing conversions of literals assigned
// to the wchar_t arrays above don't result in values that will be treated as errors by the
// conversion functions.
if (is_wchar_ucs2()) return;
test_utf82wchar(u4, sizeof(u4), w4, sizeof(w4) / sizeof(*w4), 0, sizeof(w4) / sizeof(*w4),
"u4/w4 4 octets chars");
test_wchar2utf8(w4, sizeof(w4) / sizeof(*w4), u4, sizeof(u4), 0, sizeof(u4),
"w4/u4 4 octets chars");
test_wchar2utf8(wb, sizeof(wb) / sizeof(*wb), ub, sizeof(ub), 0, 0, "wb/ub bad chars");
test_wchar2utf8(wb, sizeof(wb) / sizeof(*wb), ub, sizeof(ub), UTF8_IGNORE_ERROR, sizeof(ub),
"wb/ub ignore bad chars");
test_wchar2utf8(wm, sizeof(wm) / sizeof(*wm), um, sizeof(um), 0, sizeof(um),
"wm/um mixed languages");
test_wchar2utf8(wm, sizeof(wm) / sizeof(*wm), um, sizeof(um) - 1, 0, 0, "wm/um boundaries -1");
@ -1010,20 +1001,34 @@ static void test_utf8() {
"wm/um boundaries +1");
test_wchar2utf8(wm, sizeof(wm) / sizeof(*wm), nullc, 0, 0, sizeof(um),
"wm/um calculate length");
test_utf82wchar(um, sizeof(um), wm, sizeof(wm) / sizeof(*wm), 0, sizeof(wm) / sizeof(*wm),
"um/wm mixed languages");
test_utf82wchar(um, sizeof(um), wm, sizeof(wm) / sizeof(*wm) + 1, 0, sizeof(wm) / sizeof(*wm),
"um/wm boundaries +1");
test_utf82wchar(um, sizeof(um), NULL, 0, 0, sizeof(wm) / sizeof(*wm), "um/wm calculate length");
// The following tests won't pass on systems (e.g., Cygwin) where sizeof wchar_t is 2. That's
// due to several reasons but the primary one is that narrowing conversions of literals assigned
// to the wchar_t arrays above don't result in values that will be treated as errors by the
// conversion functions.
#if WCHAR_MAX != 0xffff
test_utf82wchar(u4, sizeof(u4), w4, sizeof(w4) / sizeof(*w4), 0, sizeof(w4) / sizeof(*w4),
"u4/w4 4 octets chars");
test_wchar2utf8(w4, sizeof(w4) / sizeof(*w4), u4, sizeof(u4), 0, sizeof(u4),
"w4/u4 4 octets chars");
test_wchar2utf8(wb, sizeof(wb) / sizeof(*wb), ub, sizeof(ub), 0, 0, "wb/ub bad chars");
test_wchar2utf8(wb, sizeof(wb) / sizeof(*wb), ub, sizeof(ub), UTF8_IGNORE_ERROR, sizeof(ub),
"wb/ub ignore bad chars");
test_wchar2utf8(wb, sizeof(wb) / sizeof(*wb), nullc, 0, 0, 0,
"wb calculate length of bad chars");
test_wchar2utf8(wb, sizeof(wb) / sizeof(*wb), nullc, 0, UTF8_IGNORE_ERROR, sizeof(ub),
"calculate length, ignore bad chars");
test_utf82wchar(ub1, sizeof(ub1), wb1, sizeof(wb1) / sizeof(*wb1), UTF8_IGNORE_ERROR,
sizeof(wb1) / sizeof(*wb1), "ub1/wb1 ignore bad chars");
test_utf82wchar(um, sizeof(um), wm, sizeof(wm) / sizeof(*wm), 0, sizeof(wm) / sizeof(*wm),
"um/wm mixed languages");
test_utf82wchar(um, sizeof(um), wm, sizeof(wm) / sizeof(*wm) + 1, 0, sizeof(wm) / sizeof(*wm),
"um/wm boundaries +1");
test_utf82wchar(um, sizeof(um), NULL, 0, 0, sizeof(wm) / sizeof(*wm), "um/wm calculate length");
test_utf82wchar(ub1, sizeof(ub1), NULL, 0, 0, 0, "ub1 calculate length of bad chars");
test_utf82wchar(ub1, sizeof(ub1), NULL, 0, UTF8_IGNORE_ERROR, sizeof(wb1) / sizeof(*wb1),
"ub1 calculate length, ignore bad chars");
#endif
}
static void test_escape_sequences(void) {
@ -3878,7 +3883,7 @@ long return_timezone_hour(time_t tstamp, const wchar_t *timezone) {
struct tm ltime;
char ltime_str[3];
char *str_ptr;
int n;
size_t n;
env_set(L"TZ", timezone, ENV_EXPORT);
localtime_r(&tstamp, &ltime);
@ -3930,7 +3935,7 @@ int main(int argc, char **argv) {
}
}
srand(time(0));
srand((unsigned int)time(NULL));
configure_thread_assertions_for_testing();
program_name = L"(ignore)";