diff --git a/backend/gb18030.c b/backend/gb18030.c index 89c2bd01..ac8b79d1 100644 --- a/backend/gb18030.c +++ b/backend/gb18030.c @@ -2902,7 +2902,7 @@ INTERNAL int gb18030_utf8tomb(struct zint_symbol *symbol, const unsigned char so } /* Convert UTF-8 string to single byte ECI and place in array of ints */ -INTERNAL int gb18030_utf8tosb(int eci, const unsigned char source[], size_t* p_length, unsigned int* gbdata) { +INTERNAL int gb18030_utf8tosb(int eci, const unsigned char source[], size_t* p_length, unsigned int* gbdata, int full_multibyte) { int error_number; #ifndef _MSC_VER unsigned char single_byte[*p_length + 1]; @@ -2916,42 +2916,50 @@ INTERNAL int gb18030_utf8tosb(int eci, const unsigned char source[], size_t* p_l return error_number; } - gb18030_cpy(single_byte, p_length, gbdata); + gb18030_cpy(single_byte, p_length, gbdata, full_multibyte); return 0; } -/* Copy byte input stream to array of ints, putting double-bytes that match HANXIN Chinese mode in single entry, and quad-bytes in 2 entries */ -INTERNAL void gb18030_cpy(const unsigned char source[], size_t* p_length, unsigned int* gbdata) { +/* If `full_multibyte` set, copy byte input stream to array of ints, putting double-bytes that match HANXIN Chinese mode in single entry, + * and quad-bytes in 2 entries. If `full_multibyte` not set, do a straight copy */ +INTERNAL void gb18030_cpy(const unsigned char source[], size_t* p_length, unsigned int* gbdata, int full_multibyte) { unsigned int i, j, length; int done; unsigned char c1, c2, c3, c4; - for (i = 0, j = 0, length = *p_length; i < length; i++, j++) { - done = 0; - c1 = source[i]; - if (length - i >= 2) { - if (c1 >= 0x81 && c1 <= 0xFE) { - c2 = source[i + 1]; - if ((c2 >= 0x40 && c2 <= 0x7E) || (c2 >= 0x80 && c2 <= 0xFE)) { - gbdata[j] = (c1 << 8) | c2; - i++; - done = 1; - } else if (length - i >= 4 && (c2 >= 0x30 && c2 <= 0x39)) { - c3 = source[i + 2]; - c4 = source[i + 3]; - if ((c3 >= 0x81 && c3 <= 0xFE) && (c4 >= 0x30 && c4 <= 0x39)) { - gbdata[j++] = (c1 << 8) | c2; - gbdata[j] = (c3 << 8) | c4; - i += 3; + if (full_multibyte) { + for (i = 0, j = 0, length = *p_length; i < length; i++, j++) { + done = 0; + c1 = source[i]; + if (length - i >= 2) { + if (c1 >= 0x81 && c1 <= 0xFE) { + c2 = source[i + 1]; + if ((c2 >= 0x40 && c2 <= 0x7E) || (c2 >= 0x80 && c2 <= 0xFE)) { + gbdata[j] = (c1 << 8) | c2; + i++; done = 1; + } else if (length - i >= 4 && (c2 >= 0x30 && c2 <= 0x39)) { + c3 = source[i + 2]; + c4 = source[i + 3]; + if ((c3 >= 0x81 && c3 <= 0xFE) && (c4 >= 0x30 && c4 <= 0x39)) { + gbdata[j++] = (c1 << 8) | c2; + gbdata[j] = (c3 << 8) | c4; + i += 3; + done = 1; + } } } } + if (!done) { + gbdata[j] = c1; + } } - if (!done) { - gbdata[j] = c1; + *p_length = j; + } else { + /* Straight copy */ + for (i = 0, length = *p_length; i < length; i++) { + gbdata[i] = source[i]; } } - *p_length = j; } diff --git a/backend/gb18030.h b/backend/gb18030.h index 55eaf3c8..704e4bdb 100644 --- a/backend/gb18030.h +++ b/backend/gb18030.h @@ -1,7 +1,7 @@ /* gb18030.h - Unicode to GB 18030 libzint - the open source barcode library - Copyright (C) 2009-2017 Robin Stuart + Copyright (C) 2009-2020 Robin Stuart Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions @@ -39,8 +39,8 @@ extern "C" { INTERNAL int gb18030_wctomb_zint(unsigned int* r1, unsigned int* r2, unsigned int wc); INTERNAL int gb18030_utf8tomb(struct zint_symbol *symbol, const unsigned char source[], size_t* p_length, unsigned int* gbdata); -INTERNAL int gb18030_utf8tosb(int eci, const unsigned char source[], size_t* p_length, unsigned int* gbdata); -INTERNAL void gb18030_cpy(const unsigned char source[], size_t* p_length, unsigned int* gbdata); +INTERNAL int gb18030_utf8tosb(int eci, const unsigned char source[], size_t* p_length, unsigned int* gbdata, int full_multibyte); +INTERNAL void gb18030_cpy(const unsigned char source[], size_t* p_length, unsigned int* gbdata, int full_multibyte); #ifdef __cplusplus } diff --git a/backend/gb2312.c b/backend/gb2312.c index deb934c3..276a84e0 100644 --- a/backend/gb2312.c +++ b/backend/gb2312.c @@ -1570,7 +1570,7 @@ INTERNAL int gb2312_utf8tomb(struct zint_symbol *symbol, const unsigned char sou } /* Convert UTF-8 string to single byte ECI and place in array of ints */ -INTERNAL int gb2312_utf8tosb(int eci, const unsigned char source[], size_t* p_length, unsigned int* gbdata) { +INTERNAL int gb2312_utf8tosb(int eci, const unsigned char source[], size_t* p_length, unsigned int* gbdata, int full_multibyte) { int error_number; #ifndef _MSC_VER unsigned char single_byte[*p_length + 1]; @@ -1584,30 +1584,38 @@ INTERNAL int gb2312_utf8tosb(int eci, const unsigned char source[], size_t* p_le return error_number; } - gb2312_cpy(single_byte, p_length, gbdata); + gb2312_cpy(single_byte, p_length, gbdata, full_multibyte); return 0; } -/* Copy byte input stream to array of ints, putting double-bytes that match GRIDMATRIX Chinese mode in single entry */ -INTERNAL void gb2312_cpy(const unsigned char source[], size_t* p_length, unsigned int* gbdata) { +/* If `full_multibyte` set, copy byte input stream to array of ints, putting double-bytes that match GRIDMATRIX Chinese mode in a single entry. + * If `full_multibyte` not set, do a straight copy */ +INTERNAL void gb2312_cpy(const unsigned char source[], size_t* p_length, unsigned int* gbdata, int full_multibyte) { unsigned int i, j, length; unsigned char c1, c2; - for (i = 0, j = 0, length = *p_length; i < length; i++, j++) { - if (length - i >= 2) { - c1 = source[i]; - c2 = source[i + 1]; - if (((c1 >= 0xA1 && c1 <= 0xA9) || (c1 >= 0xB0 && c1 <= 0xF7)) && c2 >= 0xA1 && c2 <= 0xFE) { - /* This may or may not be valid GB 2312 (EUC-CN), but don't care as long as it can be encoded in GRIDMATRIX Chinese mode */ - gbdata[j] = (c1 << 8) | c2; - i++; + if (full_multibyte) { + for (i = 0, j = 0, length = *p_length; i < length; i++, j++) { + if (length - i >= 2) { + c1 = source[i]; + c2 = source[i + 1]; + if (((c1 >= 0xA1 && c1 <= 0xA9) || (c1 >= 0xB0 && c1 <= 0xF7)) && c2 >= 0xA1 && c2 <= 0xFE) { + /* This may or may not be valid GB 2312 (EUC-CN), but don't care as long as it can be encoded in GRIDMATRIX Chinese mode */ + gbdata[j] = (c1 << 8) | c2; + i++; + } else { + gbdata[j] = c1; + } } else { - gbdata[j] = c1; + gbdata[j] = source[i]; } - } else { - gbdata[j] = source[i]; + } + *p_length = j; + } else { + /* Straight copy */ + for (i = 0, length = *p_length; i < length; i++) { + gbdata[i] = source[i]; } } - *p_length = j; } diff --git a/backend/gb2312.h b/backend/gb2312.h index 312e2844..b3ca91be 100644 --- a/backend/gb2312.h +++ b/backend/gb2312.h @@ -1,7 +1,7 @@ /* gb2312.h - Unicode to GB 2312-1980 (EUC-CN) libzint - the open source barcode library - Copyright (C) 2009-2017 Robin Stuart + Copyright (C) 2009-2020 Robin Stuart Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions @@ -39,8 +39,8 @@ extern "C" { INTERNAL int gb2312_wctomb_zint(unsigned int* r, unsigned int wc); INTERNAL int gb2312_utf8tomb(struct zint_symbol *symbol, const unsigned char source[], size_t* p_length, unsigned int* gbdata); -INTERNAL int gb2312_utf8tosb(int eci, const unsigned char source[], size_t* p_length, unsigned int* gbdata); -INTERNAL void gb2312_cpy(const unsigned char source[], size_t* p_length, unsigned int* gbdata); +INTERNAL int gb2312_utf8tosb(int eci, const unsigned char source[], size_t* p_length, unsigned int* gbdata, int full_multibyte); +INTERNAL void gb2312_cpy(const unsigned char source[], size_t* p_length, unsigned int* gbdata, int full_multibyte); #ifdef __cplusplus } diff --git a/backend/gridmtx.c b/backend/gridmtx.c index 98060180..a91a7253 100644 --- a/backend/gridmtx.c +++ b/backend/gridmtx.c @@ -35,7 +35,6 @@ #include #include -#include #ifdef _MSC_VER #include #endif @@ -927,6 +926,7 @@ INTERNAL int grid_matrix(struct zint_symbol *symbol, const unsigned char source[ int size, modules, error_number; int auto_layers, min_layers, layers, auto_ecc_level, min_ecc_level, ecc_level; int x, y, i; + int full_multibyte; char binary[9300]; int data_cw, input_latch = 0; unsigned char word[1460]; @@ -943,13 +943,15 @@ INTERNAL int grid_matrix(struct zint_symbol *symbol, const unsigned char source[ word[i] = 0; } + full_multibyte = symbol->option_3 == ZINT_FULL_MULTIBYTE; /* If set use Hanzi mode in DATA_MODE or for single-byte Latin */ + if ((symbol->input_mode & 0x07) == DATA_MODE) { - gb2312_cpy(source, &length, gbdata); + gb2312_cpy(source, &length, gbdata, full_multibyte); } else { int done = 0; if (symbol->eci != 29) { /* Unless ECI 29 (GB) */ /* Try single byte (Latin) conversion first */ - int error_number = gb2312_utf8tosb(symbol->eci && symbol->eci <= 899 ? symbol->eci : 3, source, &length, gbdata); + int error_number = gb2312_utf8tosb(symbol->eci && symbol->eci <= 899 ? symbol->eci : 3, source, &length, gbdata, full_multibyte); if (error_number == 0) { done = 1; } else if (symbol->eci && symbol->eci <= 899) { diff --git a/backend/hanxin.c b/backend/hanxin.c index cac60cc8..15dff6bf 100644 --- a/backend/hanxin.c +++ b/backend/hanxin.c @@ -34,7 +34,6 @@ #include #include -#include #ifdef _MSC_VER #include #endif @@ -1377,6 +1376,7 @@ INTERNAL int han_xin(struct zint_symbol *symbol, const unsigned char source[], s int est_binlen; int ecc_level = symbol->option_1; int i, j, version; + int full_multibyte; int data_codewords = 0, size; int codewords; int bitmask; @@ -1398,13 +1398,15 @@ INTERNAL int han_xin(struct zint_symbol *symbol, const unsigned char source[], s unsigned char *grid; #endif + full_multibyte = symbol->option_3 == ZINT_FULL_MULTIBYTE; /* If set use Hanzi mode in DATA_MODE or for single-byte Latin */ + if ((symbol->input_mode & 0x07) == DATA_MODE) { - gb18030_cpy(source, &length, gbdata); + gb18030_cpy(source, &length, gbdata, full_multibyte); } else { int done = 0; if (symbol->eci != 29) { /* Unless ECI 29 (GB) */ /* Try single byte (Latin) conversion first */ - int error_number = gb18030_utf8tosb(symbol->eci && symbol->eci <= 899 ? symbol->eci : 3, source, &length, gbdata); + int error_number = gb18030_utf8tosb(symbol->eci && symbol->eci <= 899 ? symbol->eci : 3, source, &length, gbdata, full_multibyte); if (error_number == 0) { done = 1; } else if (symbol->eci && symbol->eci <= 899) { diff --git a/backend/qr.c b/backend/qr.c index 669d1d4d..99e09b9b 100644 --- a/backend/qr.c +++ b/backend/qr.c @@ -1526,6 +1526,7 @@ INTERNAL int qr_code(struct zint_symbol *symbol, const unsigned char source[], s int i, j, est_binlen; int ecc_level, autosize, version, max_cw, target_codewords, blocks, size; int bitmask, gs1; + int full_multibyte; int canShrink; #ifndef _MSC_VER @@ -1540,14 +1541,15 @@ INTERNAL int qr_code(struct zint_symbol *symbol, const unsigned char source[], s #endif gs1 = ((symbol->input_mode & 0x07) == GS1_MODE); + full_multibyte = symbol->option_3 == ZINT_FULL_MULTIBYTE; /* If set use Kanji mode in DATA_MODE or for single-byte Latin */ if ((symbol->input_mode & 0x07) == DATA_MODE) { - sjis_cpy(source, &length, jisdata); + sjis_cpy(source, &length, jisdata, full_multibyte); } else { int done = 0; if (symbol->eci != 20) { /* Unless ECI 20 (Shift JIS) */ /* Try single byte (Latin) conversion first */ - int error_number = sjis_utf8tosb(symbol->eci && symbol->eci <= 899 ? symbol->eci : 3, source, &length, jisdata); + int error_number = sjis_utf8tosb(symbol->eci && symbol->eci <= 899 ? symbol->eci : 3, source, &length, jisdata, full_multibyte); if (error_number == 0) { done = 1; } else if (symbol->eci && symbol->eci <= 899) { @@ -2344,6 +2346,7 @@ static int micro_apply_bitmask(unsigned char *grid,const int size) { INTERNAL int microqr(struct zint_symbol *symbol, const unsigned char source[], size_t length) { size_t i, size, j; char full_stream[200]; + int full_multibyte; unsigned int jisdata[40]; char mode[40]; @@ -2381,11 +2384,13 @@ INTERNAL int microqr(struct zint_symbol *symbol, const unsigned char source[], s ecc_level = symbol->option_1; } + full_multibyte = symbol->option_3 == ZINT_FULL_MULTIBYTE; /* If set use Kanji mode in DATA_MODE or for single-byte Latin */ + if ((symbol->input_mode & 0x07) == DATA_MODE) { - sjis_cpy(source, &length, jisdata); + sjis_cpy(source, &length, jisdata, full_multibyte); } else { /* Try ISO 8859-1 conversion first */ - int error_number = sjis_utf8tosb(3, source, &length, jisdata); + int error_number = sjis_utf8tosb(3, source, &length, jisdata, full_multibyte); if (error_number != 0) { /* Try Shift-JIS */ error_number = sjis_utf8tomb(symbol, source, &length, jisdata); @@ -2866,6 +2871,7 @@ INTERNAL int rmqr(struct zint_symbol *symbol, const unsigned char source[], size int i, j, est_binlen; int ecc_level, autosize, version, max_cw, target_codewords, blocks, h_size, v_size; int gs1; + int full_multibyte; int footprint, best_footprint, format_data; unsigned int left_format_info, right_format_info; @@ -2881,12 +2887,13 @@ INTERNAL int rmqr(struct zint_symbol *symbol, const unsigned char source[], size #endif gs1 = ((symbol->input_mode & 0x07) == GS1_MODE); + full_multibyte = symbol->option_3 == ZINT_FULL_MULTIBYTE; /* If set use Kanji mode in DATA_MODE or for single-byte Latin */ if ((symbol->input_mode & 0x07) == DATA_MODE) { - sjis_cpy(source, &length, jisdata); + sjis_cpy(source, &length, jisdata, full_multibyte); } else { /* Try ISO 8859-1 conversion first */ - int error_number = sjis_utf8tosb(3, source, &length, jisdata); + int error_number = sjis_utf8tosb(3, source, &length, jisdata, full_multibyte); if (error_number != 0) { /* Try Shift-JIS */ error_number = sjis_utf8tomb(symbol, source, &length, jisdata); diff --git a/backend/sjis.c b/backend/sjis.c index b553f9ba..908e8810 100644 --- a/backend/sjis.c +++ b/backend/sjis.c @@ -1537,7 +1537,7 @@ INTERNAL int sjis_utf8tomb(struct zint_symbol *symbol, const unsigned char sourc } /* Convert UTF-8 string to single byte ECI and place in array of ints */ -INTERNAL int sjis_utf8tosb(int eci, const unsigned char source[], size_t* p_length, unsigned int* jisdata) { +INTERNAL int sjis_utf8tosb(int eci, const unsigned char source[], size_t* p_length, unsigned int* jisdata, int full_multibyte) { int error_number; #ifndef _MSC_VER unsigned char single_byte[*p_length + 1]; @@ -1551,30 +1551,38 @@ INTERNAL int sjis_utf8tosb(int eci, const unsigned char source[], size_t* p_leng return error_number; } - sjis_cpy(single_byte, p_length, jisdata); + sjis_cpy(single_byte, p_length, jisdata, full_multibyte); return 0; } -/* Copy byte input stream to array of ints, putting double-bytes that match QR Kanji mode in single entry */ -INTERNAL void sjis_cpy(const unsigned char source[], size_t* p_length, unsigned int* jisdata) { +/* If `full_multibyte` set, copy byte input stream to array of ints, putting double-bytes that match QR Kanji mode in a single entry. + * If `full_multibyte` not set, do a straight copy */ +INTERNAL void sjis_cpy(const unsigned char source[], size_t* p_length, unsigned int* jisdata, int full_multibyte) { unsigned int i, j, jis, length; unsigned char c; - for (i = 0, j = 0, length = *p_length; i < length; i++, j++) { - c = source[i]; - if (((c >= 0x81 && c <= 0x9F) || (c >= 0xE0 && c <= 0xEB)) && length - i >= 2) { - jis = (c << 8) | source[i + 1]; - if ((jis >= 0x8140 && jis <= 0x9FFC) || (jis >= 0xE040 && jis <= 0xEBBF)) { - /* This may or may not be valid Shift JIS, but don't care as long as it can be encoded in QR Kanji mode */ - jisdata[j] = jis; - i++; + if (full_multibyte) { + for (i = 0, j = 0, length = *p_length; i < length; i++, j++) { + c = source[i]; + if (((c >= 0x81 && c <= 0x9F) || (c >= 0xE0 && c <= 0xEB)) && length - i >= 2) { + jis = (c << 8) | source[i + 1]; + if ((jis >= 0x8140 && jis <= 0x9FFC) || (jis >= 0xE040 && jis <= 0xEBBF)) { + /* This may or may not be valid Shift JIS, but don't care as long as it can be encoded in QR Kanji mode */ + jisdata[j] = jis; + i++; + } else { + jisdata[j] = c; + } } else { jisdata[j] = c; } - } else { - jisdata[j] = c; + } + *p_length = j; + } else { + /* Straight copy */ + for (i = 0, length = *p_length; i < length; i++) { + jisdata[i] = source[i]; } } - *p_length = j; } diff --git a/backend/sjis.h b/backend/sjis.h index 8647180a..b019a1b0 100644 --- a/backend/sjis.h +++ b/backend/sjis.h @@ -1,7 +1,7 @@ /* sjis.h - Unicode to Shift JIS libzint - the open source barcode library - Copyright (C) 2009-2017 Robin Stuart + Copyright (C) 2009-2020 Robin Stuart Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions @@ -39,8 +39,8 @@ extern "C" { INTERNAL int sjis_wctomb_zint(unsigned int* r, unsigned int wc); INTERNAL int sjis_utf8tomb(struct zint_symbol *symbol, const unsigned char source[], size_t* p_length, unsigned int* jisdata); -INTERNAL int sjis_utf8tosb(int eci, const unsigned char source[], size_t* p_length, unsigned int* jisdata); -INTERNAL void sjis_cpy(const unsigned char source[], size_t* p_length, unsigned int* jisdata); +INTERNAL int sjis_utf8tosb(int eci, const unsigned char source[], size_t* p_length, unsigned int* jisdata, int full_multibyte); +INTERNAL void sjis_cpy(const unsigned char source[], size_t* p_length, unsigned int* jisdata, int full_multibyte); #ifdef __cplusplus } diff --git a/backend/tests/test_gb18030.c b/backend/tests/test_gb18030.c index 0c91b058..4ffb3d29 100644 --- a/backend/tests/test_gb18030.c +++ b/backend/tests/test_gb18030.c @@ -157,7 +157,7 @@ static void test_gb18030_utf8tomb(void) int length; int ret; size_t ret_length; - unsigned int expected_gbdata[20]; + unsigned int expected_gbdata[30]; char* comment; }; // é U+00E9 in ISO 8859-1 plus other ISO 8859 (but not in ISO 8859-7 or ISO 8859-11), Win 1250 plus other Win, in GB 18030 0xA8A6, UTF-8 C3A9 @@ -184,7 +184,7 @@ static void test_gb18030_utf8tomb(void) int data_size = sizeof(data) / sizeof(struct item); struct zint_symbol symbol; - unsigned int gbdata[20]; + unsigned int gbdata[30]; for (int i = 0; i < data_size; i++) { @@ -211,11 +211,12 @@ static void test_gb18030_utf8tosb(void) int ret; struct item { int eci; + int full_multibyte; unsigned char* data; int length; int ret; size_t ret_length; - unsigned int expected_gbdata[20]; + unsigned int expected_gbdata[30]; char* comment; }; // é U+00E9 in ISO 8859-1 0xE9, Win 1250 plus other Win, in HANXIN Chinese mode first byte range 0x81..FE @@ -226,31 +227,44 @@ static void test_gb18030_utf8tosb(void) // 9 U+0039 in ASCII 0x39, outside first byte range, outside double-byte second byte range and quad-byte third byte range, in quad-byte second/fourth byte ranges // s/\/\*[ 0-9]*\*\//\=printf("\/*%3d*\/", line(".") - line("'<")) struct item data[] = { - /* 0*/ { 3, "é", -1, 0, 1, { 0xE9 }, "First byte in range but only one byte" }, - /* 1*/ { 3, "β", -1, ZINT_ERROR_INVALID_DATA, -1, {}, "Not in ECI 3 (ISO 8859-1)" }, - /* 2*/ { 9, "β", -1, 0, 1, { 0xE2 }, "In ECI 9 (ISO 8859-7)" }, - /* 3*/ { 3, "¥", -1, 0, 1, { 0xA5 }, "First byte in range but only one byte" }, - /* 4*/ { 3, "¥é", -1, 0, 1, { 0xA5E9 }, "In double-byte range" }, - /* 5*/ { 3, "¥ÿ", -1, 0, 2, { 0xA5, 0xFF }, "First byte in range but not second" }, - /* 6*/ { 3, "¥9é9", -1, 0, 2, { 0xA539, 0xE939 }, "In quad-byte range" }, - /* 7*/ { 3, "¥9", -1, 0, 2, { 0xA5, 0x39 }, "In quad-byte first/second range but only 2 bytes, not in double-byte range" }, - /* 8*/ { 3, "¥9é", -1, 0, 3, { 0xA5, 0x39, 0xE9 }, "In quad-byte first/second/third range but only 3 bytes, no bytes in double-byte range" }, - /* 9*/ { 3, "¥9é@", -1, 0, 3, { 0xA5, 0x39, 0xE940 }, "In quad-byte first/second/third range but not fourth, second 2 bytes in double-byte range" }, - /* 10*/ { 3, "¥@é9", -1, 0, 3, { 0xA540, 0xE9, 0x39 }, "In quad-byte first/third/fourth range but not second, first 2 bytes in double-byte range" }, - /* 11*/ { 3, "¥9@9", -1, 0, 4, { 0xA5, 0x39, 0x40, 0x39 }, "In quad-byte first/second/fourth range but not third, no bytes in double-byte range" }, - /* 12*/ { 3, "é9éé¥9é@¥9é9¥9é0é@@¥¥é0é1", -1, 0, 15, { 0xE9, 0x39, 0xE9E9, 0xA5, 0x39, 0xE940, 0xA539, 0xE939, 0xA539, 0xE930, 0xE940, 0x40, 0xA5A5, 0xE930, 0xE931 }, "" }, + /* 1*/ { 3, 0, "é", -1, 0, 1, { 0xE9 }, "Not full multibyte" }, + /* 2*/ { 3, 1, "é", -1, 0, 1, { 0xE9 }, "First byte in range but only one byte" }, + /* 3*/ { 3, 0, "β", -1, ZINT_ERROR_INVALID_DATA, -1, {}, "Not full multibyte" }, + /* 4*/ { 3, 1, "β", -1, ZINT_ERROR_INVALID_DATA, -1, {}, "Not in ECI 3 (ISO 8859-1)" }, + /* 5*/ { 9, 0, "β", -1, 0, 1, { 0xE2 }, "Not full multibyte" }, + /* 6*/ { 9, 1, "β", -1, 0, 1, { 0xE2 }, "In ECI 9 (ISO 8859-7)" }, + /* 7*/ { 3, 0, "¥", -1, 0, 1, { 0xA5 }, "Not full multibyte" }, + /* 8*/ { 3, 1, "¥", -1, 0, 1, { 0xA5 }, "First byte in range but only one byte" }, + /* 9*/ { 3, 0, "¥é", -1, 0, 2, { 0xA5, 0xE9 }, "Not full multibyte" }, + /* 10*/ { 3, 1, "¥é", -1, 0, 1, { 0xA5E9 }, "In double-byte range" }, + /* 11*/ { 3, 0, "¥ÿ", -1, 0, 2, { 0xA5, 0xFF }, "Not full multibyte" }, + /* 12*/ { 3, 1, "¥ÿ", -1, 0, 2, { 0xA5, 0xFF }, "First byte in range but not second" }, + /* 13*/ { 3, 0, "¥9é9", -1, 0, 4, { 0xA5, 0x39, 0xE9, 0x39 }, "Not full multibyte" }, + /* 14*/ { 3, 1, "¥9é9", -1, 0, 2, { 0xA539, 0xE939 }, "In quad-byte range" }, + /* 15*/ { 3, 0, "¥9", -1, 0, 2, { 0xA5, 0x39 }, "Not full multibyte" }, + /* 16*/ { 3, 1, "¥9", -1, 0, 2, { 0xA5, 0x39 }, "In quad-byte first/second range but only 2 bytes, not in double-byte range" }, + /* 17*/ { 3, 0, "¥9é", -1, 0, 3, { 0xA5, 0x39, 0xE9 }, "Not full multibyte" }, + /* 18*/ { 3, 1, "¥9é", -1, 0, 3, { 0xA5, 0x39, 0xE9 }, "In quad-byte first/second/third range but only 3 bytes, no bytes in double-byte range" }, + /* 19*/ { 3, 0, "¥9é@", -1, 0, 4, { 0xA5, 0x39, 0xE9, 0x40 }, "Not full multibyte" }, + /* 20*/ { 3, 1, "¥9é@", -1, 0, 3, { 0xA5, 0x39, 0xE940 }, "In quad-byte first/second/third range but not fourth, second 2 bytes in double-byte range" }, + /* 21*/ { 3, 0, "¥@é9", -1, 0, 4, { 0xA5, 0x40, 0xE9, 0x39 }, "Not full multibyte" }, + /* 22*/ { 3, 1, "¥@é9", -1, 0, 3, { 0xA540, 0xE9, 0x39 }, "In quad-byte first/third/fourth range but not second, first 2 bytes in double-byte range" }, + /* 23*/ { 3, 0, "¥9@9", -1, 0, 4, { 0xA5, 0x39, 0x40, 0x39 }, "Not full multibyte" }, + /* 24*/ { 3, 1, "¥9@9", -1, 0, 4, { 0xA5, 0x39, 0x40, 0x39 }, "In quad-byte first/second/fourth range but not third, no bytes in double-byte range" }, + /* 25*/ { 3, 0, "é9éé¥9é@¥9é9¥9é0é@@¥¥é0é1", -1, 0, 25, { 0xE9, 0x39, 0xE9, 0xE9, 0xA5, 0x39, 0xE9, 0x40, 0xA5, 0x39, 0xE9, 0x39, 0xA5, 0x39, 0xE9, 0x30, 0xE9, 0x40, 0x40, 0xA5, 0xA5, 0xE9, 0x30, 0xE9, 0x31 }, "" }, + /* 26*/ { 3, 1, "é9éé¥9é@¥9é9¥9é0é@@¥¥é0é1", -1, 0, 15, { 0xE9, 0x39, 0xE9E9, 0xA5, 0x39, 0xE940, 0xA539, 0xE939, 0xA539, 0xE930, 0xE940, 0x40, 0xA5A5, 0xE930, 0xE931 }, "" }, }; int data_size = sizeof(data) / sizeof(struct item); - unsigned int gbdata[20]; + unsigned int gbdata[30]; for (int i = 0; i < data_size; i++) { int length = data[i].length == -1 ? strlen(data[i].data) : data[i].length; size_t ret_length = length; - ret = gb18030_utf8tosb(data[i].eci, data[i].data, &ret_length, gbdata); + ret = gb18030_utf8tosb(data[i].eci, data[i].data, &ret_length, gbdata, data[i].full_multibyte); assert_equal(ret, data[i].ret, "i:%d ret %d != %d\n", i, ret, data[i].ret); if (ret == 0) { assert_equal(ret_length, data[i].ret_length, "i:%d ret_length %zu != %zu\n", i, ret_length, data[i].ret_length); @@ -269,32 +283,38 @@ static void test_gb18030_cpy(void) int ret; struct item { + int full_multibyte; unsigned char* data; int length; int ret; size_t ret_length; - unsigned int expected_gbdata[20]; + unsigned int expected_gbdata[30]; char* comment; }; // s/\/\*[ 0-9]*\*\//\=printf("\/*%3d*\/", line(".") - line("'<")) struct item data[] = { - /* 0*/ { "\351", -1, 0, 1, { 0xE9 }, "In HANXIN Chinese mode first-byte range but only one byte" }, - /* 1*/ { "\351\241", -1, 0, 1, { 0xE9A1 }, "In HANXIN Chinese range" }, - /* 2*/ { "\241", -1, 0, 1, { 0xA1 }, "In first-byte range but only one byte" }, - /* 3*/ { "\241\241", -1, 0, 1, { 0xA1A1 }, "In range" }, - /* 4*/ { "\241\240\241\376\367\376\367\377\2012\2013", -1, 0, 7, { 0xA1A0, 0xA1FE, 0xF7FE, 0xF7, 0xFF, 0x8132, 0x8133 }, "" }, + /* 0*/ { 0, "\351", -1, 0, 1, { 0xE9 }, "Not full multibyte" }, + /* 1*/ { 1, "\351", -1, 0, 1, { 0xE9 }, "In HANXIN Chinese mode first-byte range but only one byte" }, + /* 2*/ { 0, "\351\241", -1, 0, 2, { 0xE9, 0xA1 }, "Not full multibyte" }, + /* 3*/ { 1, "\351\241", -1, 0, 1, { 0xE9A1 }, "In HANXIN Chinese range" }, + /* 4*/ { 0, "\241", -1, 0, 1, { 0xA1 }, "Not full multibyte" }, + /* 5*/ { 1, "\241", -1, 0, 1, { 0xA1 }, "In first-byte range but only one byte" }, + /* 6*/ { 0, "\241\241", -1, 0, 2, { 0xA1, 0xA1 }, "Not full multibyte" }, + /* 7*/ { 1, "\241\241", -1, 0, 1, { 0xA1A1 }, "In range" }, + /* 8*/ { 0, "\241\240\241\376\367\376\367\377\2012\2013", -1, 0, 12, { 0xA1, 0xA0, 0xA1, 0xFE, 0xF7, 0xFE, 0xF7, 0xFF, 0x81, 0x32, 0x81, 0x33 }, "" }, + /* 9*/ { 1, "\241\240\241\376\367\376\367\377\2012\2013", -1, 0, 7, { 0xA1A0, 0xA1FE, 0xF7FE, 0xF7, 0xFF, 0x8132, 0x8133 }, "" }, }; int data_size = sizeof(data) / sizeof(struct item); - unsigned int gbdata[20]; + unsigned int gbdata[30]; for (int i = 0; i < data_size; i++) { int length = data[i].length == -1 ? strlen(data[i].data) : data[i].length; size_t ret_length = length; - gb18030_cpy(data[i].data, &ret_length, gbdata); + gb18030_cpy(data[i].data, &ret_length, gbdata, data[i].full_multibyte); assert_equal(ret_length, data[i].ret_length, "i:%d ret_length %zu != %zu\n", i, ret_length, data[i].ret_length); for (int j = 0; j < ret_length; j++) { assert_equal(gbdata[j], data[i].expected_gbdata[j], "i:%d gbdata[%d] %04X != %04X\n", i, j, gbdata[j], data[i].expected_gbdata[j]); diff --git a/backend/tests/test_gb2312.c b/backend/tests/test_gb2312.c index f3130396..f1797aa4 100644 --- a/backend/tests/test_gb2312.c +++ b/backend/tests/test_gb2312.c @@ -152,6 +152,7 @@ static void test_gb2312_utf8tosb(void) int ret; struct item { int eci; + int full_multibyte; unsigned char* data; int length; int ret; @@ -173,15 +174,24 @@ static void test_gb2312_utf8tosb(void) // ÿ U+00FF in ISO 8859-1 0xFF, outside first byte and second byte range // s/\/\*[ 0-9]*\*\//\=printf("\/*%3d*\/", line(".") - line("'<")) struct item data[] = { - /* 0*/ { 3, "é", -1, 0, 1, { 0xE9 }, "First byte in range but only one byte" }, - /* 1*/ { 3, "β", -1, ZINT_ERROR_INVALID_DATA, -1, {}, "Not in ECI 3 (ISO 8859-1)" }, - /* 2*/ { 9, "β", -1, 0, 1, { 0xE2 }, "In ECI 9 (ISO 8859-7)" }, - /* 3*/ { 3, "¥", -1, 0, 1, { 0xA5 }, "First byte in range but only one byte" }, - /* 4*/ { 3, "¡é", -1, 0, 1, { 0xA1E9 }, "In GRIDMATRIX Chinese mode range" }, - /* 5*/ { 3, "¡\302\240", -1, 0, 2, { 0xA1, 0xA0 }, "First byte in range but not second" }, - /* 6*/ { 3, "©é", -1, 0, 1, { 0xA9E9 }, "In GRIDMATRIX Chinese mode range" }, - /* 7*/ { 3, "©ÿ", -1, 0, 2, { 0xA9, 0xFF }, "First byte in range but not second" }, - /* 8*/ { 3, "éaé驪ª©¯é°°é÷éø", -1, 0, 10, { 0xE9, 0x61, 0xE9E9, 0xA9AA, 0xAA, 0xA9AF, 0xE9B0, 0xB0E9, 0xF7E9, 0xF8 }, "" }, + /* 0*/ { 3, 0, "é", -1, 0, 1, { 0xE9 }, "Not full multibyte" }, + /* 1*/ { 3, 1, "é", -1, 0, 1, { 0xE9 }, "First byte in range but only one byte" }, + /* 2*/ { 3, 0, "β", -1, ZINT_ERROR_INVALID_DATA, -1, {}, "Not in ECI 3 (ISO 8859-1)" }, + /* 3*/ { 3, 1, "β", -1, ZINT_ERROR_INVALID_DATA, -1, {}, "Not in ECI 3 (ISO 8859-1)" }, + /* 4*/ { 9, 0, "β", -1, 0, 1, { 0xE2 }, "In ECI 9 (ISO 8859-7)" }, + /* 5*/ { 9, 1, "β", -1, 0, 1, { 0xE2 }, "In ECI 9 (ISO 8859-7)" }, + /* 6*/ { 3, 0, "¥", -1, 0, 1, { 0xA5 }, "Not full multibyte" }, + /* 7*/ { 3, 1, "¥", -1, 0, 1, { 0xA5 }, "First byte in range but only one byte" }, + /* 8*/ { 3, 0, "¡é", -1, 0, 2, { 0xA1, 0xE9 }, "Not full multibyte" }, + /* 9*/ { 3, 1, "¡é", -1, 0, 1, { 0xA1E9 }, "In GRIDMATRIX Chinese mode range" }, + /* 10*/ { 3, 0, "¡\302\240", -1, 0, 2, { 0xA1, 0xA0 }, "Not full multibyte" }, + /* 11*/ { 3, 1, "¡\302\240", -1, 0, 2, { 0xA1, 0xA0 }, "First byte in range but not second" }, + /* 12*/ { 3, 0, "©é", -1, 0, 2, { 0xA9, 0xE9 }, "Not full multibyte" }, + /* 13*/ { 3, 1, "©é", -1, 0, 1, { 0xA9E9 }, "In GRIDMATRIX Chinese mode range" }, + /* 14*/ { 3, 0, "©ÿ", -1, 0, 2, { 0xA9, 0xFF }, "Not full multibyte" }, + /* 15*/ { 3, 1, "©ÿ", -1, 0, 2, { 0xA9, 0xFF }, "First byte in range but not second" }, + /* 16*/ { 3, 0, "éaé驪ª©¯é°°é÷éø", -1, 0, 16, { 0xE9, 0x61, 0xE9, 0xE9, 0xA9, 0xAA, 0xAA, 0xA9, 0xAF, 0xE9, 0xB0, 0xB0, 0xE9, 0xF7, 0xE9, 0xF8 }, "" }, + /* 17*/ { 3, 1, "éaé驪ª©¯é°°é÷éø", -1, 0, 10, { 0xE9, 0x61, 0xE9E9, 0xA9AA, 0xAA, 0xA9AF, 0xE9B0, 0xB0E9, 0xF7E9, 0xF8 }, "" }, }; int data_size = sizeof(data) / sizeof(struct item); @@ -193,7 +203,7 @@ static void test_gb2312_utf8tosb(void) int length = data[i].length == -1 ? strlen(data[i].data) : data[i].length; size_t ret_length = length; - ret = gb2312_utf8tosb(data[i].eci, data[i].data, &ret_length, gbdata); + ret = gb2312_utf8tosb(data[i].eci, data[i].data, &ret_length, gbdata, data[i].full_multibyte); assert_equal(ret, data[i].ret, "i:%d ret %d != %d\n", i, ret, data[i].ret); if (ret == 0) { assert_equal(ret_length, data[i].ret_length, "i:%d ret_length %zu != %zu\n", i, ret_length, data[i].ret_length); @@ -212,6 +222,7 @@ static void test_gb2312_cpy(void) int ret; struct item { + int full_multibyte; unsigned char* data; int length; int ret; @@ -221,11 +232,16 @@ static void test_gb2312_cpy(void) }; // s/\/\*[ 0-9]*\*\//\=printf("\/*%3d*\/", line(".") - line("'<")) struct item data[] = { - /* 0*/ { "\351", -1, 0, 1, { 0xE9 }, "In GRIDMATRIX Chinese mode first-byte range but only one byte" }, - /* 1*/ { "\351\241", -1, 0, 1, { 0xE9A1 }, "In GRIDMATRIX Chinese range" }, - /* 2*/ { "\241", -1, 0, 1, { 0xA1 }, "In first-byte range but only one byte" }, - /* 3*/ { "\241\241", -1, 0, 1, { 0xA1A1 }, "In range" }, - /* 4*/ { "\241\240\241\376\367\376\367\377", -1, 0, 6, { 0xA1, 0xA0, 0xA1FE, 0xF7FE, 0xF7, 0xFF }, "" }, + /* 0*/ { 0, "\351", -1, 0, 1, { 0xE9 }, "Not full multibyte" }, + /* 1*/ { 1, "\351", -1, 0, 1, { 0xE9 }, "In GRIDMATRIX Chinese mode first-byte range but only one byte" }, + /* 2*/ { 0, "\351\241", -1, 0, 2, { 0xE9, 0xA1 }, "Not full multibyte" }, + /* 3*/ { 1, "\351\241", -1, 0, 1, { 0xE9A1 }, "In GRIDMATRIX Chinese range" }, + /* 4*/ { 0, "\241", -1, 0, 1, { 0xA1 }, "Not full multibyte" }, + /* 5*/ { 1, "\241", -1, 0, 1, { 0xA1 }, "In first-byte range but only one byte" }, + /* 6*/ { 0, "\241\241", -1, 0, 2, { 0xA1, 0xA1 }, "Not full multibyte" }, + /* 7*/ { 1, "\241\241", -1, 0, 1, { 0xA1A1 }, "In range" }, + /* 8*/ { 0, "\241\240\241\376\367\376\367\377", -1, 0, 8, { 0xA1, 0xA0, 0xA1, 0xFE, 0xF7, 0xFE, 0xF7, 0xFF }, "" }, + /* 9*/ { 1, "\241\240\241\376\367\376\367\377", -1, 0, 6, { 0xA1, 0xA0, 0xA1FE, 0xF7FE, 0xF7, 0xFF }, "" }, }; int data_size = sizeof(data) / sizeof(struct item); @@ -237,7 +253,7 @@ static void test_gb2312_cpy(void) int length = data[i].length == -1 ? strlen(data[i].data) : data[i].length; size_t ret_length = length; - gb2312_cpy(data[i].data, &ret_length, gbdata); + gb2312_cpy(data[i].data, &ret_length, gbdata, data[i].full_multibyte); assert_equal(ret_length, data[i].ret_length, "i:%d ret_length %zu != %zu\n", i, ret_length, data[i].ret_length); for (int j = 0; j < ret_length; j++) { assert_equal(gbdata[j], data[i].expected_gbdata[j], "i:%d gbdata[%d] %04X != %04X\n", i, j, gbdata[j], data[i].expected_gbdata[j]); diff --git a/backend/tests/test_gridmtx.c b/backend/tests/test_gridmtx.c index 7d630d82..09f30e2e 100644 --- a/backend/tests/test_gridmtx.c +++ b/backend/tests/test_gridmtx.c @@ -1,6 +1,6 @@ /* libzint - the open source barcode library - Copyright (C) 2008-2019 Robin Stuart + Copyright (C) 2008-2020 Robin Stuart Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions @@ -98,6 +98,7 @@ static void test_input(void) struct item { int input_mode; int eci; + int option_3; unsigned char* data; int ret; int expected_eci; @@ -110,54 +111,58 @@ static void test_input(void) // ㈩ U+3229 in GB 2312 0x226E // 一 U+4E00 in GB 2312 0x523B struct item data[] = { - /* 0*/ { UNICODE_MODE, 0, "é", 0, 0, "30 01 69 00", "B1 (ISO 8859-1)" }, - /* 1*/ { UNICODE_MODE, 3, "é", 0, 3, "60 01 58 00 74 40", "ECI-3 B1 (ISO 8859-1)" }, - /* 2*/ { UNICODE_MODE, 29, "é", 0, 29, "60 0E 44 2A 37 7C 00", "ECI-29 H1 (GB 2312)" }, - /* 3*/ { UNICODE_MODE, 26, "é", 0, 26, "60 0D 05 28 4F 7C 00", "ECI-26 H1 (UTF-8)" }, - /* 4*/ { DATA_MODE, 0, "é", 0, 0, "0A 51 1F 78 00", "H1 (UTF-8)" }, - /* 5*/ { DATA_MODE, 0, "\351", 0, 0, "30 01 69 00", "B1 (ISO 8859-1) (0xE9)" }, - /* 6*/ { UNICODE_MODE, 0, "β", 0, 0, "08 40 2F 78 00", "H1 (GB 2312)" }, - /* 7*/ { UNICODE_MODE, 9, "β", 0, 9, "60 04 58 00 71 00", "ECI-9 B1 (ISO 8859-7)" }, - /* 8*/ { UNICODE_MODE, 29, "β", 0, 29, "60 0E 44 20 17 7C 00", "ECI-29 H1 (GB 2312)" }, - /* 9*/ { UNICODE_MODE, 26, "β", 0, 26, "60 0D 05 6B 17 7C 00", "ECI-26 H1 (UTF-8)" }, - /* 10*/ { DATA_MODE, 0, "β", 0, 0, "0B 56 2F 78 00", "H1 (UTF-8)" }, - /* 11*/ { UNICODE_MODE, 0, "ÿ", 0, 0, "30 01 7F 00", "B1 (ISO 8859-1)" }, - /* 12*/ { UNICODE_MODE, 0, "ÿÿÿ", 0, 0, "30 05 7F 7F 7F 60", "B3 (ISO 8859-1)" }, - /* 13*/ { UNICODE_MODE, 0, "㈩一", 0, 0, "08 15 68 0E 7F 70 00", "H2 (GB 2312)" }, - /* 14*/ { UNICODE_MODE, 29, "㈩一", 0, 29, "60 0E 44 0A 74 07 3F 78 00", "ECI-29 H2 (GB 2312)" }, - /* 15*/ { DATA_MODE, 0, "\177\177", 0, 0, "30 02 7F 3F 40", "B2 (ASCII)" }, - /* 16*/ { DATA_MODE, 0, "\177\177\177", 0, 0, "30 04 7F 3F 5F 60", "B3 (ASCII)" }, - /* 17*/ { UNICODE_MODE, 0, "123", 0, 0, "10 1E 7F 68", "N3 (ASCII)" }, - /* 18*/ { UNICODE_MODE, 0, " 123", 0, 0, "11 7A 03 6F 7D 00", "N4 (ASCII)" }, - /* 19*/ { UNICODE_MODE, 0, "1+23", 0, 0, "11 7B 03 6F 7D 00", "N4 (ASCII)" }, - /* 20*/ { UNICODE_MODE, 0, "12.3", 0, 0, "11 7C 63 6F 7D 00", "N4 (ASCII)" }, - /* 21*/ { UNICODE_MODE, 0, "123,", 0, 0, "10 1E 7F 73 76 5E 60", "N3 L1 (ASCII)" }, - /* 22*/ { UNICODE_MODE, 0, "123,4", 0, 0, "14 1E 7F 51 48 3F 50", "N5 (ASCII)" }, - /* 23*/ { UNICODE_MODE, 0, "\015\012123", 0, 0, "11 7D 63 6F 7D 00", "N4 (ASCII) (EOL)" }, - /* 24*/ { UNICODE_MODE, 0, "1\015\01223", 0, 0, "11 7E 03 6F 7D 00", "N4 (ASCII) (EOL)" }, - /* 25*/ { UNICODE_MODE, 0, "12\015\0123", 0, 0, "11 7E 23 6F 7D 00", "N4 (ASCII) (EOL)" }, - /* 26*/ { UNICODE_MODE, 0, "123\015\012", 0, 0, "10 1E 7F 7C 01 06 42 40", "N3 B2 (ASCII) (EOL)" }, - /* 27*/ { UNICODE_MODE, 0, "123\015\0124", 0, 0, "14 1E 7F 5D 48 3F 50", "N5 (ASCII) (EOL)" }, - /* 28*/ { UNICODE_MODE, 0, "2.2.0", 0, 0, "15 7C 46 73 78 40 07 7A", "N5 (ASCII)" }, - /* 29*/ { UNICODE_MODE, 0, "2.2.0.5", 0, 0, "30 0C 32 17 0C 45 63 01 38 6A 00", "B7 (ASCII)" }, - /* 30*/ { UNICODE_MODE, 0, "2.2.0.56", 0, 0, "13 7C 46 73 78 40 07 71 46 0F 74", "N8 (ASCII)" }, - /* 31*/ { UNICODE_MODE, 0, "1 1234ABCD12.2abcd-12", 0, 0, "13 7A 23 41 2A 3F 68 01 08 3E 4F 66 1E 5F 70 00 44 1F 2F 6E 0F 0F 74", "N6 U4 N4 L4 N3 (ASCII)" }, - /* 32*/ { UNICODE_MODE, 0, "1 123ABCDE12.2abcd-12", 0, 0, "28 1F 40 42 06 28 59 43 27 01 05 7D 56 42 49 16 34 7F 6D 30 08 2F 60", "M21 (ASCII)" }, - /* 33*/ { UNICODE_MODE, 0, "国外通信教材 Matlab6.5", 0, 0, "09 63 27 20 4E 24 1F 05 21 58 22 13 7E 1E 4C 78 09 56 00 3D 3F 4A 45 3F 50", "H6 U2 L5 N3 (GB 2312) (Same as D.2 example)" }, - /* 34*/ { UNICODE_MODE, 0, "AAT", 0, 0, "20 00 4F 30", "U3 (ASCII)" }, - /* 35*/ { UNICODE_MODE, 0, "aat", 0, 0, "18 00 4F 30", "L3 (ASCII)" }, - /* 36*/ { UNICODE_MODE, 0, "AAT2556", 0, 0, "20 00 4F 58 7F 65 47 7A", "U3 N4 (ASCII) (note same bit count as M7)" }, - /* 37*/ { UNICODE_MODE, 0, "AAT2556 ", 0, 0, "29 22 4E 42 0A 14 37 6F 60", "M8 (ASCII)" }, - /* 38*/ { UNICODE_MODE, 0, "AAT2556 电", 0, 0, "29 22 4E 42 0A 14 37 6F 62 2C 1F 7E 00", "M8 H1 (GB 2312)" }, - /* 39*/ { UNICODE_MODE, 0, " 200", 0, 0, "11 7A 06 23 7D 00", "N4 (ASCII)" }, - /* 40*/ { UNICODE_MODE, 0, " 200mA至", 0, 0, "2F 60 40 00 60 2B 78 63 41 7F 40", "M6 H1 (GB 2312)" }, - /* 41*/ { UNICODE_MODE, 0, "2A tel:86 019 82512738", 0, 0, "28 22 5F 4F 29 48 5F 6D 7E 6F 55 57 1F 28 63 0F 5A 11 64 0F 74", "M2 L5(with control) N15 (ASCII)" }, - /* 42*/ { UNICODE_MODE, 0, "至2A tel:86 019 82512738", 0, 0, "30 07 56 60 4C 48 13 6A 32 17 7B 3F 5B 75 35 67 6A 18 63 76 44 39 03 7D 00", "B4 L5(with control) N15 (GB 2312)" }, - /* 43*/ { UNICODE_MODE, 0, "AAT2556 电池充电器+降压转换器 200mA至2A tel:86 019 82512738", 0, 0, "(62) 29 22 22 1C 4E 41 42 7E 0A 40 14 00 37 7E 6F 00 62 7E 2C 00 1C 7E 4B 00 41 7E 18 00", "M8 H11 M6 B4 L5(with control) N15 (GB 2312) (*NOT SAME* as D3 example, M8 H11 M6 H1 M3 L4(with control) N15, which uses a few more bits)" }, - /* 44*/ { UNICODE_MODE, 0, "::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::", 0, 0, "(588) 37 68 68 68 68 68 74 7E 74 74 74 74 74 3A 3A 3A 3A 3A 3A 3A 1D 1D 1D 1D 1D 1D 1D 0E", "B512 (ASCII)" }, - /* 45*/ { UNICODE_MODE, 0, "::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::\177", 0, 0, "(591) 37 68 68 68 68 68 74 7E 74 74 74 74 74 3A 3A 3A 3A 3A 3A 3A 1D 1D 1D 1D 1D 1D 1D 0E", "B513 (ASCII)" }, - /* 46*/ { UNICODE_MODE, 0, ":::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::至", 0, 0, "(591) 37 68 68 68 68 68 74 7C 74 74 74 74 74 3A 3A 3A 3A 3A 3A 3A 1D 1D 1D 1D 1D 1D 1D 0E", "B511 H1 (GB 2312)" }, - /* 47*/ { UNICODE_MODE, 0, ":::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::至:", 0, 0, "(592) 37 68 68 68 68 68 74 7E 74 74 74 74 74 3A 3A 3A 3A 3A 3A 3A 1D 1D 1D 1D 1D 1D 1D 0E", "B513 (GB 2312)" }, + /* 0*/ { UNICODE_MODE, 0, -1, "é", 0, 0, "30 01 69 00", "B1 (ISO 8859-1)" }, + /* 1*/ { UNICODE_MODE, 3, -1, "é", 0, 3, "60 01 58 00 74 40", "ECI-3 B1 (ISO 8859-1)" }, + /* 2*/ { UNICODE_MODE, 29, -1, "é", 0, 29, "60 0E 44 2A 37 7C 00", "ECI-29 H1 (GB 2312)" }, + /* 3*/ { UNICODE_MODE, 26, -1, "é", 0, 26, "60 0D 18 01 61 6A 20", "ECI-26 B2 (UTF-8)" }, + /* 4*/ { UNICODE_MODE, 26, 200, "é", 0, 26, "60 0D 05 28 4F 7C 00", "ECI-26 H1 (UTF-8) (full multibyte)" }, + /* 5*/ { DATA_MODE, 0, -1, "é", 0, 0, "30 03 43 54 40", "B2 (UTF-8)" }, + /* 6*/ { DATA_MODE, 0, 200, "é", 0, 0, "0A 51 1F 78 00", "H1 (UTF-8) (full multibyte)" }, + /* 7*/ { DATA_MODE, 0, -1, "\351", 0, 0, "30 01 69 00", "B1 (ISO 8859-1) (0xE9)" }, + /* 8*/ { UNICODE_MODE, 0, -1, "β", 0, 0, "08 40 2F 78 00", "H1 (GB 2312)" }, + /* 9*/ { UNICODE_MODE, 9, -1, "β", 0, 9, "60 04 58 00 71 00", "ECI-9 B1 (ISO 8859-7)" }, + /* 10*/ { UNICODE_MODE, 29, -1, "β", 0, 29, "60 0E 44 20 17 7C 00", "ECI-29 H1 (GB 2312)" }, + /* 11*/ { UNICODE_MODE, 26, -1, "β", 0, 26, "60 0D 18 01 67 2C 40", "ECI-26 H1 (UTF-8)" }, + /* 12*/ { UNICODE_MODE, 26, 200, "β", 0, 26, "60 0D 05 6B 17 7C 00", "ECI-26 H1 (UTF-8) (full multibyte)" }, + /* 13*/ { DATA_MODE, 0, -1, "β", 0, 0, "30 03 4E 59 00", "B2 (UTF-8)" }, + /* 14*/ { DATA_MODE, 0, 200, "β", 0, 0, "0B 56 2F 78 00", "H1 (UTF-8) (full multibyte)" }, + /* 15*/ { UNICODE_MODE, 0, -1, "ÿ", 0, 0, "30 01 7F 00", "B1 (ISO 8859-1)" }, + /* 16*/ { UNICODE_MODE, 0, -1, "ÿÿÿ", 0, 0, "30 05 7F 7F 7F 60", "B3 (ISO 8859-1)" }, + /* 17*/ { UNICODE_MODE, 0, -1, "㈩一", 0, 0, "08 15 68 0E 7F 70 00", "H2 (GB 2312)" }, + /* 18*/ { UNICODE_MODE, 29, -1, "㈩一", 0, 29, "60 0E 44 0A 74 07 3F 78 00", "ECI-29 H2 (GB 2312)" }, + /* 19*/ { DATA_MODE, 0, -1, "\177\177", 0, 0, "30 02 7F 3F 40", "B2 (ASCII)" }, + /* 20*/ { DATA_MODE, 0, -1, "\177\177\177", 0, 0, "30 04 7F 3F 5F 60", "B3 (ASCII)" }, + /* 21*/ { UNICODE_MODE, 0, -1, "123", 0, 0, "10 1E 7F 68", "N3 (ASCII)" }, + /* 22*/ { UNICODE_MODE, 0, -1, " 123", 0, 0, "11 7A 03 6F 7D 00", "N4 (ASCII)" }, + /* 23*/ { UNICODE_MODE, 0, -1, "1+23", 0, 0, "11 7B 03 6F 7D 00", "N4 (ASCII)" }, + /* 24*/ { UNICODE_MODE, 0, -1, "12.3", 0, 0, "11 7C 63 6F 7D 00", "N4 (ASCII)" }, + /* 25*/ { UNICODE_MODE, 0, -1, "123,", 0, 0, "10 1E 7F 73 76 5E 60", "N3 L1 (ASCII)" }, + /* 26*/ { UNICODE_MODE, 0, -1, "123,4", 0, 0, "14 1E 7F 51 48 3F 50", "N5 (ASCII)" }, + /* 27*/ { UNICODE_MODE, 0, -1, "\015\012123", 0, 0, "11 7D 63 6F 7D 00", "N4 (ASCII) (EOL)" }, + /* 28*/ { UNICODE_MODE, 0, -1, "1\015\01223", 0, 0, "11 7E 03 6F 7D 00", "N4 (ASCII) (EOL)" }, + /* 29*/ { UNICODE_MODE, 0, -1, "12\015\0123", 0, 0, "11 7E 23 6F 7D 00", "N4 (ASCII) (EOL)" }, + /* 30*/ { UNICODE_MODE, 0, -1, "123\015\012", 0, 0, "10 1E 7F 7C 01 06 42 40", "N3 B2 (ASCII) (EOL)" }, + /* 31*/ { UNICODE_MODE, 0, -1, "123\015\0124", 0, 0, "14 1E 7F 5D 48 3F 50", "N5 (ASCII) (EOL)" }, + /* 32*/ { UNICODE_MODE, 0, -1, "2.2.0", 0, 0, "15 7C 46 73 78 40 07 7A", "N5 (ASCII)" }, + /* 33*/ { UNICODE_MODE, 0, -1, "2.2.0.5", 0, 0, "30 0C 32 17 0C 45 63 01 38 6A 00", "B7 (ASCII)" }, + /* 34*/ { UNICODE_MODE, 0, -1, "2.2.0.56", 0, 0, "13 7C 46 73 78 40 07 71 46 0F 74", "N8 (ASCII)" }, + /* 35*/ { UNICODE_MODE, 0, -1, "1 1234ABCD12.2abcd-12", 0, 0, "13 7A 23 41 2A 3F 68 01 08 3E 4F 66 1E 5F 70 00 44 1F 2F 6E 0F 0F 74", "N6 U4 N4 L4 N3 (ASCII)" }, + /* 36*/ { UNICODE_MODE, 0, -1, "1 123ABCDE12.2abcd-12", 0, 0, "28 1F 40 42 06 28 59 43 27 01 05 7D 56 42 49 16 34 7F 6D 30 08 2F 60", "M21 (ASCII)" }, + /* 37*/ { UNICODE_MODE, 0, -1, "国外通信教材 Matlab6.5", 0, 0, "09 63 27 20 4E 24 1F 05 21 58 22 13 7E 1E 4C 78 09 56 00 3D 3F 4A 45 3F 50", "H6 U2 L5 N3 (GB 2312) (Same as D.2 example)" }, + /* 38*/ { UNICODE_MODE, 0, -1, "AAT", 0, 0, "20 00 4F 30", "U3 (ASCII)" }, + /* 39*/ { UNICODE_MODE, 0, -1, "aat", 0, 0, "18 00 4F 30", "L3 (ASCII)" }, + /* 40*/ { UNICODE_MODE, 0, -1, "AAT2556", 0, 0, "20 00 4F 58 7F 65 47 7A", "U3 N4 (ASCII) (note same bit count as M7)" }, + /* 41*/ { UNICODE_MODE, 0, -1, "AAT2556 ", 0, 0, "29 22 4E 42 0A 14 37 6F 60", "M8 (ASCII)" }, + /* 42*/ { UNICODE_MODE, 0, -1, "AAT2556 电", 0, 0, "29 22 4E 42 0A 14 37 6F 62 2C 1F 7E 00", "M8 H1 (GB 2312)" }, + /* 43*/ { UNICODE_MODE, 0, -1, " 200", 0, 0, "11 7A 06 23 7D 00", "N4 (ASCII)" }, + /* 44*/ { UNICODE_MODE, 0, -1, " 200mA至", 0, 0, "2F 60 40 00 60 2B 78 63 41 7F 40", "M6 H1 (GB 2312)" }, + /* 45*/ { UNICODE_MODE, 0, -1, "2A tel:86 019 82512738", 0, 0, "28 22 5F 4F 29 48 5F 6D 7E 6F 55 57 1F 28 63 0F 5A 11 64 0F 74", "M2 L5(with control) N15 (ASCII)" }, + /* 46*/ { UNICODE_MODE, 0, -1, "至2A tel:86 019 82512738", 0, 0, "30 07 56 60 4C 48 13 6A 32 17 7B 3F 5B 75 35 67 6A 18 63 76 44 39 03 7D 00", "B4 L5(with control) N15 (GB 2312)" }, + /* 47*/ { UNICODE_MODE, 0, -1, "AAT2556 电池充电器+降压转换器 200mA至2A tel:86 019 82512738", 0, 0, "(62) 29 22 22 1C 4E 41 42 7E 0A 40 14 00 37 7E 6F 00 62 7E 2C 00 1C 7E 4B 00 41 7E 18 00", "M8 H11 M6 B4 L5(with control) N15 (GB 2312) (*NOT SAME* as D3 example, M8 H11 M6 H1 M3 L4(with control) N15, which uses a few more bits)" }, + /* 48*/ { UNICODE_MODE, 0, -1, "::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::", 0, 0, "(588) 37 68 68 68 68 68 74 7E 74 74 74 74 74 3A 3A 3A 3A 3A 3A 3A 1D 1D 1D 1D 1D 1D 1D 0E", "B512 (ASCII)" }, + /* 49*/ { UNICODE_MODE, 0, -1, "::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::\177", 0, 0, "(591) 37 68 68 68 68 68 74 7E 74 74 74 74 74 3A 3A 3A 3A 3A 3A 3A 1D 1D 1D 1D 1D 1D 1D 0E", "B513 (ASCII)" }, + /* 50*/ { UNICODE_MODE, 0, -1, ":::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::至", 0, 0, "(591) 37 68 68 68 68 68 74 7C 74 74 74 74 74 3A 3A 3A 3A 3A 3A 3A 1D 1D 1D 1D 1D 1D 1D 0E", "B511 H1 (GB 2312)" }, + /* 51*/ { UNICODE_MODE, 0, -1, ":::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::至:", 0, 0, "(592) 37 68 68 68 68 68 74 7E 74 74 74 74 74 3A 3A 3A 3A 3A 3A 3A 1D 1D 1D 1D 1D 1D 1D 0E", "B513 (GB 2312)" }, }; int data_size = sizeof(data) / sizeof(struct item); @@ -171,6 +176,9 @@ static void test_input(void) symbol->symbology = BARCODE_GRIDMATRIX; symbol->input_mode = data[i].input_mode; symbol->eci = data[i].eci; + if (data[i].option_3 != -1) { + symbol->option_3 = data[i].option_3; + } symbol->debug = ZINT_DEBUG_TEST; // Needed to get codeword dump in errtxt int length = strlen(data[i].data); @@ -179,9 +187,9 @@ static void test_input(void) assert_equal(ret, data[i].ret, "i:%d ZBarcode_Encode ret %d != %d\n", i, ret, data[i].ret); #ifdef TEST_INPUT_GENERATE_EXPECTED - printf(" /*%3d*/ { %s, %d, \"%s\", %s, %d, \"%s\", \"%s\" },\n", - i, testUtilInputModeName(data[i].input_mode), data[i].eci, testUtilEscape(data[i].data, length, escaped, sizeof(escaped)), testUtilErrorName(data[i].ret), - ret < 5 ? symbol->eci : -1, symbol->errtxt, data[i].comment); + printf(" /*%3d*/ { %s, %d, %d, \"%s\", %s, %d, \"%s\", \"%s\" },\n", + i, testUtilInputModeName(data[i].input_mode), data[i].eci, data[i].option_3, testUtilEscape(data[i].data, length, escaped, sizeof(escaped)), + testUtilErrorName(data[i].ret), ret < 5 ? symbol->eci : -1, symbol->errtxt, data[i].comment); #else if (ret < 5) { diff --git a/backend/tests/test_hanxin.c b/backend/tests/test_hanxin.c index 2ac5c47a..b318cec4 100644 --- a/backend/tests/test_hanxin.c +++ b/backend/tests/test_hanxin.c @@ -103,6 +103,7 @@ static void test_input(void) struct item { int input_mode; int eci; + int option_3; unsigned char* data; int length; int ret; @@ -113,38 +114,47 @@ static void test_input(void) // é U+00E9 in ISO 8859-1 plus other ISO 8859 (but not in ISO 8859-7 or ISO 8859-11), Win 1250 plus other Win, in GB 18030 0xA8A6, UTF-8 C3A9 // β U+03B2 in ISO 8859-7 Greek 0xE2 (but not other ISO 8859 or Win page), in GB 18030 0xA6C2, UTF-8 CEB2 // ÿ U+00FF in ISO 8859-1 0xFF, not in GB 18030, outside first byte and second byte range, UTF-8 C3BF + // PAD U+0080 GB 18030 4-byte Region 0x81308130, UTF-8 C280 (\302\200) // 啊 U+554A GB 18030 Region One 0xB0A1, UTF-8 E5958A // 亍 U+4E8D GB 18030 Region Two 0xD8A1, UTF-8 E4BA8D // 齄 U+9F44 GB 18030 Region Two 0xF7FE, UTF-8 E9BD84 // 丂 U+4E02 GB 18030 2-byte Region 0x8140, UTF-8 E4B882 - // PAD U+0080 GB 18030 4-byte Region 0x81308130, UTF-8 C280 (\302\200) // � (REPLACEMENT CHARACTER) U+FFFD GB 18030 4-byte Region 0x81308130, UTF-8 EFBFBD (\357\277\275) struct item data[] = { - /* 0*/ { UNICODE_MODE, 0, "é", -1, 0, 0, "30 00 F4 80 00 00 00 00 00", "B1 (ISO 8859-1)" }, - /* 1*/ { UNICODE_MODE, 3, "é", -1, 0, 3, "80 33 00 0F 48 00 00 00 00", "ECI-3 B1 (ISO 8859-1)" }, - /* 2*/ { UNICODE_MODE, 29, "é", -1, 0, 29, "81 D4 FC FF FF 00 00 00 00", "ECI-29 H(1)1 (GB 18030) (Region One)" }, - /* 3*/ { UNICODE_MODE, 26, "é", -1, 0, 26, "81 A4 70 2F FF 00 00 00 00", "ECI-26 H(1)1 (UTF-8) (Region One)" }, - /* 4*/ { DATA_MODE, 0, "é", -1, 0, 0, "47 02 FF F0 00 00 00 00 00", "H(1)1 (UTF-8) (Region One)" }, - /* 5*/ { DATA_MODE, 0, "\351", -1, 0, 0, "30 00 F4 80 00 00 00 00 00", "B1 (ISO 8859-1) (0xE9)" }, - /* 6*/ { UNICODE_MODE, 0, "β", -1, 0, 0, "30 01 53 61 00 00 00 00 00", "B2 (GB 18030) (2-byte Region)" }, - /* 7*/ { UNICODE_MODE, 9, "β", -1, 0, 9, "80 93 00 0F 10 00 00 00 00", "ECI-9 B1 (ISO 8859-7)" }, - /* 8*/ { UNICODE_MODE, 29, "β", -1, 0, 29, "81 D3 00 15 36 10 00 00 00", "ECI-29 B2 (GB 18030) (2-byte Region)" }, - /* 9*/ { UNICODE_MODE, 26, "β", -1, 0, 26, "81 A4 B1 5F FF 00 00 00 00", "ECI-26 H(1)1 (UTF-8) (Region One)" }, - /* 10*/ { DATA_MODE, 0, "β", -1, 0, 0, "4B 15 FF F0 00 00 00 00 00", "H(1)1 (UTF-8) (Region One)" }, - /* 11*/ { UNICODE_MODE, 0, "ÿ", -1, 0, 0, "30 00 FF 80 00 00 00 00 00", "B1 (ISO 8859-1)" }, - /* 12*/ { UNICODE_MODE, 0, "ÿÿÿ", -1, 0, 0, "30 01 FF FF FF 80 00 00 00", "B3 (ISO 8859-1)" }, - /* 13*/ { UNICODE_MODE, 0, "\302\200", -1, 0, 0, "70 00 00 00 00 00 00 00 00", "H(f)1 (GB 18030) (4-byte Region)" }, - /* 14*/ { UNICODE_MODE, 0, "\302\200�", -1, 0, 0, "70 00 00 38 26 7E 40 00 00", "H(f)2 (GB 18030) (both 4-byte Region)" }, - /* 15*/ { UNICODE_MODE, 0, "啊亍齄丂\302\200", -1, 0, 0, "64 68 50 3C AC 28 80 00 FF FE E0 00 00 00 00 00 00", "H(d)4 H(f)1 (GB 18030)" }, - /* 16*/ { DATA_MODE, 0, "\177\177", -1, 0, 0, "2F BD F7 F0 00 00 00 00 00", "T2 (ASCII)" }, - /* 17*/ { DATA_MODE, 0, "\177\177\177", -1, 0, 0, "2F BD F7 DF C0 00 00 00 00", "T3 (ASCII)" }, - /* 18*/ { UNICODE_MODE, 0, "123", -1, 0, 0, "11 EF FF 00 00 00 00 00 00", "N3 (ASCII)" }, - /* 19*/ { UNICODE_MODE, 0, "12345", -1, 0, 0, "11 EC 2D FF 80 00 00 00 00", "N5 (ASCII)" }, - /* 20*/ { UNICODE_MODE, 0, "Aa%$Bb9", -1, 0, 0, "22 A4 FA 18 3E 2E 52 7F 00", "T7 (ASCII)" }, - /* 21*/ { UNICODE_MODE, 0, "Summer Palace Ticket for 6 June 2015 13:00;2015年6月6日夜01時00分PM頤和園のチケット;2015년6월6일13시오후여름궁전티켓.2015年6月6号下午13:00的颐和园门票;", -1, 0, 0, "(189) 27 38 C3 0A 35 F9 CF 99 92 F9 26 A3 E7 3E 76 C9 AE A3 7F CC 08 04 0C CD EE 44 06 C4", "T20 B64 N4 H(f)1 T1 H(f)1 T1 H(f)1 T2 H(f)9 B35 (GB 18030)" }, - /* 22*/ { UNICODE_MODE, 0, "\000\014\033 #/059:<@AMZ", 15, 0, 0, "2F 80 31 B7 1F AF E0 05 27 EB 2E CB E2 96 8F F0 00", "T15 (ASCII)" }, - /* 23*/ { UNICODE_MODE, 0, "Z[\\`alz{~\177", -1, 0, 0, "28 FE CF 4E 3E 92 FF 7E E7 CF 7F 00 00", "T10 (ASCII)" }, - /* 24*/ { UNICODE_MODE, 26, "\2021\2033", -1, 0, 26, "81 A7 01 B1 D8 00 00 00 00", "ECI-26 H(f)1 (GB 18030)" }, + /* 0*/ { UNICODE_MODE, 0, -1, "é", -1, 0, 0, "30 00 F4 80 00 00 00 00 00", "B1 (ISO 8859-1)" }, + /* 1*/ { UNICODE_MODE, 3, -1, "é", -1, 0, 3, "80 33 00 0F 48 00 00 00 00", "ECI-3 B1 (ISO 8859-1)" }, + /* 2*/ { UNICODE_MODE, 29, -1, "é", -1, 0, 29, "81 D4 FC FF FF 00 00 00 00", "ECI-29 H(1)1 (GB 18030) (Region One)" }, + /* 3*/ { UNICODE_MODE, 26, -1, "é", -1, 0, 26, "81 A3 00 16 1D 48 00 00 00", "ECI-26 B2 (UTF-8)" }, + /* 4*/ { UNICODE_MODE, 26, 200, "é", -1, 0, 26, "81 A4 70 2F FF 00 00 00 00", "ECI-26 H(1)1 (Region One) (UTF-8) (full multibyte)" }, + /* 5*/ { DATA_MODE, 0, -1, "é", -1, 0, 0, "30 01 61 D4 80 00 00 00 00", "B2 (UTF-8)" }, + /* 6*/ { DATA_MODE, 0, 200, "é", -1, 0, 0, "47 02 FF F0 00 00 00 00 00", "H(1)1 (UTF-8) (Region One) (full multibyte)" }, + /* 7*/ { DATA_MODE, 0, -1, "\351", -1, 0, 0, "30 00 F4 80 00 00 00 00 00", "B1 (ISO 8859-1) (0xE9)" }, + /* 8*/ { UNICODE_MODE, 0, -1, "β", -1, 0, 0, "30 01 53 61 00 00 00 00 00", "B2 (GB 18030) (2-byte Region)" }, + /* 9*/ { UNICODE_MODE, 9, -1, "β", -1, 0, 9, "80 93 00 0F 10 00 00 00 00", "ECI-9 B1 (ISO 8859-7)" }, + /* 10*/ { UNICODE_MODE, 29, -1, "β", -1, 0, 29, "81 D3 00 15 36 10 00 00 00", "ECI-29 B2 (GB 18030) (2-byte Region)" }, + /* 11*/ { UNICODE_MODE, 26, -1, "β", -1, 0, 26, "81 A3 00 16 75 90 00 00 00", "ECI-26 B2 (UTF-8)" }, + /* 12*/ { UNICODE_MODE, 26, 200, "β", -1, 0, 26, "81 A4 B1 5F FF 00 00 00 00", "ECI-26 B2 (UTF-8) (full multibyte)" }, + /* 13*/ { DATA_MODE, 0, -1, "β", -1, 0, 0, "30 01 67 59 00 00 00 00 00", "B2 (UTF-8)" }, + /* 14*/ { DATA_MODE, 0, 200, "β", -1, 0, 0, "4B 15 FF F0 00 00 00 00 00", "H(1)1 (UTF-8) (Region One) (full multibyte)" }, + /* 15*/ { UNICODE_MODE, 0, -1, "ÿ", -1, 0, 0, "30 00 FF 80 00 00 00 00 00", "B1 (ISO 8859-1)" }, + /* 16*/ { UNICODE_MODE, 0, -1, "ÿÿÿ", -1, 0, 0, "30 01 FF FF FF 80 00 00 00", "B3 (ISO 8859-1)" }, + /* 17*/ { UNICODE_MODE, 0, -1, "\302\200", -1, 0, 0, "70 00 00 00 00 00 00 00 00", "H(f)1 (GB 18030) (4-byte Region) (not DATA_MODE so GB 18030 mapping)" }, + /* 18*/ { UNICODE_MODE, 0, 200, "\302\200", -1, 0, 0, "70 00 00 00 00 00 00 00 00", "H(f)1 (GB 18030) (4-byte Region)" }, + /* 19*/ { DATA_MODE, 0, 0, "\302\200", -1, 0, 0, "30 01 61 40 00 00 00 00 00", "B2 (UTF-8)" }, + /* 20*/ { DATA_MODE, 0, 200, "\302\200", -1, 0, 0, "30 01 61 40 00 00 00 00 00", "B2 (UTF-8) (full multibyte)" }, + /* 21*/ { UNICODE_MODE, 0, -1, "\302\200�", -1, 0, 0, "70 00 00 38 26 7E 40 00 00", "H(f)2 (GB 18030) (both 4-byte Region) (not DATA_MODE so GB 18030 mapping)" }, + /* 22*/ { UNICODE_MODE, 0, 200, "\302\200�", -1, 0, 0, "70 00 00 38 26 7E 40 00 00", "H(f)2 (GB 18030) (both 4-byte Region)" }, + /* 23*/ { UNICODE_MODE, 0, -1, "啊亍齄丂\302\200", -1, 0, 0, "64 68 50 3C AC 28 80 00 FF FE E0 00 00 00 00 00 00", "H(d)4 H(f)1 (GB 18030)" }, + /* 24*/ { DATA_MODE, 0, -1, "\177\177", -1, 0, 0, "2F BD F7 F0 00 00 00 00 00", "T2 (ASCII)" }, + /* 25*/ { DATA_MODE, 0, -1, "\177\177\177", -1, 0, 0, "2F BD F7 DF C0 00 00 00 00", "T3 (ASCII)" }, + /* 26*/ { UNICODE_MODE, 0, -1, "123", -1, 0, 0, "11 EF FF 00 00 00 00 00 00", "N3 (ASCII)" }, + /* 27*/ { UNICODE_MODE, 0, -1, "12345", -1, 0, 0, "11 EC 2D FF 80 00 00 00 00", "N5 (ASCII)" }, + /* 28*/ { UNICODE_MODE, 0, -1, "Aa%$Bb9", -1, 0, 0, "22 A4 FA 18 3E 2E 52 7F 00", "T7 (ASCII)" }, + /* 29*/ { UNICODE_MODE, 0, -1, "Summer Palace Ticket for 6 June 2015 13:00;2015年6月6日夜01時00分PM頤和園のチケット;2015년6월6일13시오후여름궁전티켓.2015年6月6号下午13:00的颐和园门票;", -1, 0, 0, "(189) 27 38 C3 0A 35 F9 CF 99 92 F9 26 A3 E7 3E 76 C9 AE A3 7F CC 08 04 0C CD EE 44 06 C4", "T20 B64 N4 H(f)1 T1 H(f)1 T1 H(f)1 T2 H(f)9 B35 (GB 18030)" }, + /* 30*/ { DATA_MODE, 0, -1, "Summer Palace Ticket for 6 June 2015 13:00;2015年6月6日夜01時00分PM頤和園のチケット;2015년6월6일13시오후여름궁전티켓.2015年6月6号下午13:00的颐和园门票;", -1, 0, 0, "(209) 27 38 C3 0A 35 F9 CF 99 92 F9 26 A3 E7 3E 76 C9 AE A3 7F CC 15 04 0C CD EE 44 06 C4", "T20 B117 (UTF-8)" }, + /* 31*/ { UNICODE_MODE, 0, -1, "\000\014\033 #/059:<@AMZ", 15, 0, 0, "2F 80 31 B7 1F AF E0 05 27 EB 2E CB E2 96 8F F0 00", "T15 (ASCII)" }, + /* 32*/ { UNICODE_MODE, 0, -1, "Z[\\`alz{~\177", -1, 0, 0, "28 FE CF 4E 3E 92 FF 7E E7 CF 7F 00 00", "T10 (ASCII)" }, + /* 33*/ { UNICODE_MODE, 26, 200, "\202\061\203\063", -1, 0, 26, "81 A7 01 B1 D8 00 00 00 00", "ECI-26 H(f)1 (GB 18030) (Invalid UTF-8, forces GB 2312/18030 utf8tosb() difference)" }, }; int data_size = sizeof(data) / sizeof(struct item); @@ -158,6 +168,9 @@ static void test_input(void) symbol->symbology = BARCODE_HANXIN; symbol->input_mode = data[i].input_mode; symbol->eci = data[i].eci; + if (data[i].option_3 != -1) { + symbol->option_3 = data[i].option_3; + } symbol->debug = ZINT_DEBUG_TEST; // Needed to get codeword dump in errtxt int length = data[i].length == -1 ? strlen(data[i].data) : data[i].length; @@ -166,9 +179,9 @@ static void test_input(void) assert_equal(ret, data[i].ret, "i:%d ZBarcode_Encode ret %d != %d (%s)\n", i, ret, data[i].ret, symbol->errtxt); #ifdef TEST_INPUT_GENERATE_EXPECTED - printf(" /*%3d*/ { %s, %d, \"%s\", %s, %d, \"%s\", \"%s\" },\n", - i, testUtilInputModeName(data[i].input_mode), data[i].eci, testUtilEscape(data[i].data, length, escaped, sizeof(escaped)), testUtilErrorName(data[i].ret), - ret < 5 ? symbol->eci : -1, symbol->errtxt, data[i].comment); + printf(" /*%3d*/ { %s, %d, %d, \"%s\", %d, %s, %d, \"%s\", \"%s\" },\n", + i, testUtilInputModeName(data[i].input_mode), data[i].eci, data[i].option_3, testUtilEscape(data[i].data, length, escaped, sizeof(escaped)), data[i].length, + testUtilErrorName(data[i].ret), ret < 5 ? symbol->eci : -1, symbol->errtxt, data[i].comment); #else if (ret < 5) { diff --git a/backend/tests/test_qr.c b/backend/tests/test_qr.c index 45178211..0b15f18e 100644 --- a/backend/tests/test_qr.c +++ b/backend/tests/test_qr.c @@ -1,6 +1,6 @@ /* libzint - the open source barcode library - Copyright (C) 2008-2019 Robin Stuart + Copyright (C) 2008-2020 Robin Stuart Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions @@ -140,6 +140,7 @@ static void test_qr_input(void) struct item { int input_mode; int eci; + int option_3; unsigned char* data; int ret; int expected_eci; @@ -159,84 +160,97 @@ static void test_qr_input(void) // 点 U+70B9 kanji, in Shift JIS 0x935F (\223\137), UTF-8 E782B9 // 茗 U+8317 kanji, in Shift JIS 0xE4AA (\344\252), UTF-8 E88C97 // テ U+30C6 katakana, in Shift JIS 0x8365 (\203\145), UTF-8 E38386 + // Á U+00C1, UTF-8 C381; ȁ U+0201, UTF-8 C881; Ȃ U+0202, UTF-8 C882; ¢ U+00A2, UTF-8 C2A2; á U+00E1, UTF-8 C3A1 struct item data[] = { - /* 0*/ { UNICODE_MODE, 0, "é", 0, 0, "40 1E 90 EC 11 EC 11 EC 11", "B1 (ISO 8859-1)" }, - /* 1*/ { UNICODE_MODE, 3, "é", 0, 3, "70 34 01 E9 00 EC 11 EC 11", "ECI-3 B1 (ISO 8859-1)" }, - /* 2*/ { UNICODE_MODE, 20, "é", ZINT_ERROR_INVALID_DATA, -1, "Error 800: Invalid character in input data", "é not in Shift JIS" }, - /* 3*/ { UNICODE_MODE, 26, "é", 0, 26, "71 A4 02 C3 A9 00 EC 11 EC", "ECI-26 B2 (UTF-8)" }, - /* 4*/ { DATA_MODE, 0, "é", 0, 0, "40 2C 3A 90 EC 11 EC 11 EC", "B2 (UTF-8)" }, - /* 5*/ { DATA_MODE, 0, "\351", 0, 0, "40 1E 90 EC 11 EC 11 EC 11", "B1 (ISO 8859-1)" }, - /* 6*/ { UNICODE_MODE, 0, "β", 0, 0, "80 11 00 00 EC 11 EC 11 EC", "K1 (Shift JIS)" }, - /* 7*/ { UNICODE_MODE, 9, "β", 0, 9, "70 94 01 E2 00 EC 11 EC 11", "ECI-9 B1 (ISO 8859-7)" }, - /* 8*/ { UNICODE_MODE, 20, "β", 0, 20, "71 48 01 10 00 00 EC 11 EC", "ECI-20 K1 (Shift JIS)" }, - /* 9*/ { UNICODE_MODE, 26, "β", 0, 26, "71 A4 02 CE B2 00 EC 11 EC", "ECI-26 B2 (UTF-8)" }, - /* 10*/ { DATA_MODE, 0, "β", 0, 0, "40 2C EB 20 EC 11 EC 11 EC", "B2 (UTF-8)" }, - /* 11*/ { UNICODE_MODE, 0, "ก", ZINT_WARN_USES_ECI, 13, "Warning 70 D4 01 A1 00 EC 11 EC 11", "ECI-13 B1 (ISO 8859-11)" }, - /* 12*/ { UNICODE_MODE, 13, "ก", 0, 13, "70 D4 01 A1 00 EC 11 EC 11", "ECI-13 B1 (ISO 8859-11)" }, - /* 13*/ { UNICODE_MODE, 20, "ก", ZINT_ERROR_INVALID_DATA, -1, "Error 800: Invalid character in input data", "ก not in Shift JIS" }, - /* 14*/ { UNICODE_MODE, 26, "ก", 0, 26, "71 A4 03 E0 B8 81 00 EC 11", "ECI-26 B3 (UTF-8)" }, - /* 15*/ { DATA_MODE, 0, "ก", 0, 0, "40 3E 0B 88 10 EC 11 EC 11", "B3 (UTF-8)" }, - /* 16*/ { UNICODE_MODE, 0, "Ж", 0, 0, "80 11 23 80 EC 11 EC 11 EC", "K1 (Shift JIS)" }, - /* 17*/ { UNICODE_MODE, 7, "Ж", 0, 7, "70 74 01 B6 00 EC 11 EC 11", "ECI-7 B1 (ISO 8859-5)" }, - /* 18*/ { UNICODE_MODE, 20, "Ж", 0, 20, "71 48 01 12 38 00 EC 11 EC", "ECI-20 K1 (Shift JIS)" }, - /* 19*/ { UNICODE_MODE, 26, "Ж", 0, 26, "71 A4 02 D0 96 00 EC 11 EC", "ECI-26 B2 (UTF-8)" }, - /* 20*/ { DATA_MODE, 0, "Ж", 0, 0, "40 2D 09 60 EC 11 EC 11 EC", "B2 (UTF-8)" }, - /* 21*/ { UNICODE_MODE, 0, "ກ", ZINT_WARN_USES_ECI, 26, "Warning 71 A4 03 E0 BA 81 00 EC 11", "ECI-26 B3 (UTF-8)" }, - /* 22*/ { UNICODE_MODE, 20, "ກ", ZINT_ERROR_INVALID_DATA, -1, "Error 800: Invalid character in input data", "ກ not in Shift JIS" }, - /* 23*/ { UNICODE_MODE, 26, "ກ", 0, 26, "71 A4 03 E0 BA 81 00 EC 11", "ECI-26 B3 (UTF-8)" }, - /* 24*/ { DATA_MODE, 0, "ກ", 0, 0, "40 3E 0B A8 10 EC 11 EC 11", "B3 (UTF-8)" }, - /* 25*/ { UNICODE_MODE, 0, "\\", 0, 0, "40 15 C0 EC 11 EC 11 EC 11", "B1 (ASCII)" }, - /* 26*/ { UNICODE_MODE, 20, "\\", 0, 20, "71 48 01 00 F8 00 EC 11 EC", "ECI-20 K1 (Shift JIS)" }, - /* 27*/ { UNICODE_MODE, 20, "[", 0, 20, "71 44 01 5B 00 EC 11 EC 11", "B1 (ASCII)" }, - /* 28*/ { UNICODE_MODE, 20, "\177", 0, 20, "71 44 01 7F 00 EC 11 EC 11", "ECI-20 B1 (ASCII)" }, - /* 29*/ { UNICODE_MODE, 0, "¥", 0, 0, "40 1A 50 EC 11 EC 11 EC 11", "B1 (ISO 8859-1) (same bytes as ・ Shift JIS below, so ambiguous)" }, - /* 30*/ { UNICODE_MODE, 3, "¥", 0, 3, "70 34 01 A5 00 EC 11 EC 11", "ECI-3 B1 (ISO 8859-1)" }, - /* 31*/ { UNICODE_MODE, 20, "¥", 0, 20, "71 44 01 5C 00 EC 11 EC 11", "ECI-20 B1 (Shift JIS) (to single-byte backslash codepoint 5C, so byte mode)" }, - /* 32*/ { UNICODE_MODE, 26, "¥", 0, 26, "71 A4 02 C2 A5 00 EC 11 EC", "ECI-26 B2 (UTF-8)" }, - /* 33*/ { DATA_MODE, 0, "¥", 0, 0, "40 2C 2A 50 EC 11 EC 11 EC", "B2 (UTF-8)" }, - /* 34*/ { UNICODE_MODE, 0, "・", 0, 0, "40 1A 50 EC 11 EC 11 EC 11", "B1 (Shift JIS) single-byte codepoint A5 (same bytes as ¥ ISO 8859-1 above, so ambiguous)" }, - /* 35*/ { UNICODE_MODE, 3, "・", ZINT_ERROR_INVALID_DATA, -1, "Error 575: Invalid characters in input data", "" }, - /* 36*/ { UNICODE_MODE, 20, "・", 0, 20, "71 44 01 A5 00 EC 11 EC 11", "ECI-20 B1 (Shift JIS) single-byte codepoint A5" }, - /* 37*/ { UNICODE_MODE, 26, "・", 0, 26, "71 A4 03 EF BD A5 00 EC 11", "ECI-26 B3 (UTF-8)" }, - /* 38*/ { DATA_MODE, 0, "・", 0, 0, "40 3E FB DA 50 EC 11 EC 11", "B3 (UTF-8)" }, - /* 39*/ { UNICODE_MODE, 0, "¿", 0, 0, "40 1B F0 EC 11 EC 11 EC 11", "B1 (ISO 8859-1) (same bytes as ソ Shift JIS below, so ambiguous)" }, - /* 40*/ { UNICODE_MODE, 3, "¿", 0, 3, "70 34 01 BF 00 EC 11 EC 11", "ECI-3 B1 (ISO 8859-1)" }, - /* 41*/ { UNICODE_MODE, 20, "¿", ZINT_ERROR_INVALID_DATA, -1, "Error 800: Invalid character in input data", "¿ not in Shift JIS" }, - /* 42*/ { UNICODE_MODE, 26, "¿", 0, 26, "71 A4 02 C2 BF 00 EC 11 EC", "ECI-26 B2 (UTF-8)" }, - /* 43*/ { DATA_MODE, 0, "¿", 0, 0, "40 2C 2B F0 EC 11 EC 11 EC", "B2 (UTF-8)" }, - /* 44*/ { UNICODE_MODE, 0, "ソ", 0, 0, "40 1B F0 EC 11 EC 11 EC 11", "B1 (Shift JIS) single-byte codepoint BF (same bytes as ¿ ISO 8859-1 above, so ambiguous)" }, - /* 45*/ { UNICODE_MODE, 3, "ソ", ZINT_ERROR_INVALID_DATA, -1, "Error 575: Invalid characters in input data", "" }, - /* 46*/ { UNICODE_MODE, 20, "ソ", 0, 20, "71 44 01 BF 00 EC 11 EC 11", "ECI-20 B1 (Shift JIS) single-byte codepoint BF" }, - /* 47*/ { UNICODE_MODE, 26, "ソ", 0, 26, "71 A4 03 EF BD BF 00 EC 11", "ECI-26 B3 (UTF-8)" }, - /* 48*/ { DATA_MODE, 0, "ソ", 0, 0, "40 3E FB DB F0 EC 11 EC 11", "B3 (UTF-8)" }, - /* 49*/ { UNICODE_MODE, 0, "~", 0, 0, "40 17 E0 EC 11 EC 11 EC 11", "B1 (ASCII) (same bytes as ‾ Shift JIS below, so ambiguous)" }, - /* 50*/ { UNICODE_MODE, 3, "~", 0, 3, "70 34 01 7E 00 EC 11 EC 11", "ECI-3 B1 (ASCII)" }, - /* 51*/ { UNICODE_MODE, 20, "~", ZINT_ERROR_INVALID_DATA, -1, "Error 800: Invalid character in input data", "tilde not in Shift JIS (codepoint used for overline)" }, - /* 52*/ { UNICODE_MODE, 0, "‾", 0, 0, "40 17 E0 EC 11 EC 11 EC 11", "B1 (Shift JIS) single-byte codepoint 7E (same bytes as ~ ASCII above, so ambiguous)" }, - /* 53*/ { UNICODE_MODE, 3, "‾", ZINT_ERROR_INVALID_DATA, -1, "Error 575: Invalid characters in input data", "" }, - /* 54*/ { UNICODE_MODE, 20, "‾", 0, 20, "71 44 01 7E 00 EC 11 EC 11", "ECI-20 B1 (Shift JIS) (to single-byte tilde codepoint 7E, so byte mode)" }, - /* 55*/ { UNICODE_MODE, 26, "‾", 0, 26, "71 A4 03 E2 80 BE 00 EC 11", "ECI-26 B3 (UTF-8)" }, - /* 56*/ { DATA_MODE, 0, "‾", 0, 0, "40 3E 28 0B E0 EC 11 EC 11", "B3 (UTF-8)" }, - /* 57*/ { UNICODE_MODE, 0, "点", 0, 0, "80 16 CF 80 EC 11 EC 11 EC", "K1 (Shift JIS)" }, - /* 58*/ { UNICODE_MODE, 3, "点", ZINT_ERROR_INVALID_DATA, -1, "Error 575: Invalid characters in input data", "" }, - /* 59*/ { UNICODE_MODE, 20, "点", 0, 20, "71 48 01 6C F8 00 EC 11 EC", "ECI-20 K1 (Shift JIS)" }, - /* 60*/ { UNICODE_MODE, 26, "点", 0, 26, "71 A4 03 E7 82 B9 00 EC 11", "ECI-26 B3 (UTF-8)" }, - /* 61*/ { DATA_MODE, 0, "点", 0, 0, "40 3E 78 2B 90 EC 11 EC 11", "B3 (UTF-8)" }, - /* 62*/ { DATA_MODE, 0, "\223\137", 0, 0, "80 16 CF 80 EC 11 EC 11 EC", "K1 (Shift JIS)" }, - /* 63*/ { UNICODE_MODE, 0, "¥・点", 0, 0, "40 45 CA 59 35 F0 EC 11 EC", "B4 (Shift JIS) (optimized to byte mode only)" }, - /* 64*/ { UNICODE_MODE, 3, "¥・点", ZINT_ERROR_INVALID_DATA, -1, "Error 575: Invalid characters in input data", "" }, - /* 65*/ { UNICODE_MODE, 20, "¥・点", 0, 20, "71 44 04 5C A5 93 5F 00 EC", "ECI-20 B4 (Shift JIS)" }, - /* 66*/ { UNICODE_MODE, 26, "¥・点", 0, 26, "71 A4 08 C2 A5 EF BD A5 E7 82 B9 00 EC", "ECI-26 B8 (UTF-8)" }, - /* 67*/ { DATA_MODE, 0, "\134\245\223\137", 0, 0, "40 45 CA 59 35 F0 EC 11 EC", "B8 (Shift JIS)" }, - /* 68*/ { DATA_MODE, 0, "¥・点", 0, 0, "40 8C 2A 5E FB DA 5E 78 2B 90 EC 11 EC", "B8 (UTF-8)" }, - /* 69*/ { UNICODE_MODE, 0, "点茗", 0, 0, "80 26 CF EA A8 00 EC 11 EC", "K2 (Shift JIS)" }, - /* 70*/ { UNICODE_MODE, 0, "点茗テ", 0, 0, "80 36 CF EA A8 34 A0 EC 11", "K3 (Shift JIS)" }, - /* 71*/ { UNICODE_MODE, 0, "点茗テ点", 0, 0, "80 46 CF EA A8 34 AD 9F 00", "K4 (Shift JIS)" }, - /* 72*/ { UNICODE_MODE, 0, "点茗テ点茗", 0, 0, "80 56 CF EA A8 34 AD 9F D5 50 00 EC 11", "K5 (Shift JIS)" }, - /* 73*/ { UNICODE_MODE, 0, "点茗テ点茗テ", 0, 0, "80 66 CF EA A8 34 AD 9F D5 50 69 40 EC", "K6 (Shift JIS)" }, - /* 74*/ { UNICODE_MODE, 0, "点茗テ点茗テソ", 0, 0, "80 66 CF EA A8 34 AD 9F D5 50 69 50 06 FC 00 EC", "K6 B1 (Shift JIS)" }, - /* 75*/ { DATA_MODE, 0, "\223\137\344\252\203\145\223\137\344\252\203\145\277", 0, 0, "80 66 CF EA A8 34 AD 9F D5 50 69 50 06 FC 00 EC", "K6 B1 (Shift JIS)" }, - /* 76*/ { DATA_MODE, 0, "点茗テ点茗テソ", 0, 0, "41 5E 78 2B 9E 88 C9 7E 38 38 6E 78 2B 9E 88 C9 7E 38 38 6E FB DB F0 EC 11 EC 11 EC", "B21 (UTF-8)" }, + /* 0*/ { UNICODE_MODE, 0, -1, "é", 0, 0, "40 1E 90 EC 11 EC 11 EC 11", "B1 (ISO 8859-1)" }, + /* 1*/ { UNICODE_MODE, 3, -1, "é", 0, 3, "70 34 01 E9 00 EC 11 EC 11", "ECI-3 B1 (ISO 8859-1)" }, + /* 2*/ { UNICODE_MODE, 20, -1, "é", ZINT_ERROR_INVALID_DATA, -1, "Error 800: Invalid character in input data", "é not in Shift JIS" }, + /* 3*/ { UNICODE_MODE, 26, -1, "é", 0, 26, "71 A4 02 C3 A9 00 EC 11 EC", "ECI-26 B2 (UTF-8)" }, + /* 4*/ { DATA_MODE, 0, -1, "é", 0, 0, "40 2C 3A 90 EC 11 EC 11 EC", "B2 (UTF-8)" }, + /* 5*/ { DATA_MODE, 0, -1, "\351", 0, 0, "40 1E 90 EC 11 EC 11 EC 11", "B1 (ISO 8859-1)" }, + /* 6*/ { UNICODE_MODE, 0, -1, "β", 0, 0, "80 11 00 00 EC 11 EC 11 EC", "K1 (Shift JIS)" }, + /* 7*/ { UNICODE_MODE, 9, -1, "β", 0, 9, "70 94 01 E2 00 EC 11 EC 11", "ECI-9 B1 (ISO 8859-7)" }, + /* 8*/ { UNICODE_MODE, 20, -1, "β", 0, 20, "71 48 01 10 00 00 EC 11 EC", "ECI-20 K1 (Shift JIS)" }, + /* 9*/ { UNICODE_MODE, 26, -1, "β", 0, 26, "71 A4 02 CE B2 00 EC 11 EC", "ECI-26 B2 (UTF-8)" }, + /* 10*/ { DATA_MODE, 0, -1, "β", 0, 0, "40 2C EB 20 EC 11 EC 11 EC", "B2 (UTF-8)" }, + /* 11*/ { UNICODE_MODE, 0, -1, "ก", ZINT_WARN_USES_ECI, 13, "Warning 70 D4 01 A1 00 EC 11 EC 11", "ECI-13 B1 (ISO 8859-11)" }, + /* 12*/ { UNICODE_MODE, 13, -1, "ก", 0, 13, "70 D4 01 A1 00 EC 11 EC 11", "ECI-13 B1 (ISO 8859-11)" }, + /* 13*/ { UNICODE_MODE, 20, -1, "ก", ZINT_ERROR_INVALID_DATA, -1, "Error 800: Invalid character in input data", "ก not in Shift JIS" }, + /* 14*/ { UNICODE_MODE, 26, -1, "ก", 0, 26, "71 A4 03 E0 B8 81 00 EC 11", "ECI-26 B3 (UTF-8)" }, + /* 15*/ { DATA_MODE, 0, -1, "ก", 0, 0, "40 3E 0B 88 10 EC 11 EC 11", "B3 (UTF-8)" }, + /* 16*/ { UNICODE_MODE, 0, -1, "Ж", 0, 0, "80 11 23 80 EC 11 EC 11 EC", "K1 (Shift JIS)" }, + /* 17*/ { UNICODE_MODE, 7, -1, "Ж", 0, 7, "70 74 01 B6 00 EC 11 EC 11", "ECI-7 B1 (ISO 8859-5)" }, + /* 18*/ { UNICODE_MODE, 20, -1, "Ж", 0, 20, "71 48 01 12 38 00 EC 11 EC", "ECI-20 K1 (Shift JIS)" }, + /* 19*/ { UNICODE_MODE, 26, -1, "Ж", 0, 26, "71 A4 02 D0 96 00 EC 11 EC", "ECI-26 B2 (UTF-8)" }, + /* 20*/ { DATA_MODE, 0, -1, "Ж", 0, 0, "40 2D 09 60 EC 11 EC 11 EC", "B2 (UTF-8)" }, + /* 21*/ { UNICODE_MODE, 0, -1, "ກ", ZINT_WARN_USES_ECI, 26, "Warning 71 A4 03 E0 BA 81 00 EC 11", "ECI-26 B3 (UTF-8)" }, + /* 22*/ { UNICODE_MODE, 20, -1, "ກ", ZINT_ERROR_INVALID_DATA, -1, "Error 800: Invalid character in input data", "ກ not in Shift JIS" }, + /* 23*/ { UNICODE_MODE, 26, -1, "ກ", 0, 26, "71 A4 03 E0 BA 81 00 EC 11", "ECI-26 B3 (UTF-8)" }, + /* 24*/ { DATA_MODE, 0, -1, "ກ", 0, 0, "40 3E 0B A8 10 EC 11 EC 11", "B3 (UTF-8)" }, + /* 25*/ { UNICODE_MODE, 0, -1, "\\", 0, 0, "40 15 C0 EC 11 EC 11 EC 11", "B1 (ASCII)" }, + /* 26*/ { UNICODE_MODE, 20, -1, "\\", 0, 20, "71 48 01 00 F8 00 EC 11 EC", "ECI-20 K1 (Shift JIS)" }, + /* 27*/ { UNICODE_MODE, 20, -1, "[", 0, 20, "71 44 01 5B 00 EC 11 EC 11", "B1 (ASCII)" }, + /* 28*/ { UNICODE_MODE, 20, -1, "\177", 0, 20, "71 44 01 7F 00 EC 11 EC 11", "ECI-20 B1 (ASCII)" }, + /* 29*/ { UNICODE_MODE, 0, -1, "¥", 0, 0, "40 1A 50 EC 11 EC 11 EC 11", "B1 (ISO 8859-1) (same bytes as ・ Shift JIS below, so ambiguous)" }, + /* 30*/ { UNICODE_MODE, 3, -1, "¥", 0, 3, "70 34 01 A5 00 EC 11 EC 11", "ECI-3 B1 (ISO 8859-1)" }, + /* 31*/ { UNICODE_MODE, 20, -1, "¥", 0, 20, "71 44 01 5C 00 EC 11 EC 11", "ECI-20 B1 (Shift JIS) (to single-byte backslash codepoint 5C, so byte mode)" }, + /* 32*/ { UNICODE_MODE, 26, -1, "¥", 0, 26, "71 A4 02 C2 A5 00 EC 11 EC", "ECI-26 B2 (UTF-8)" }, + /* 33*/ { DATA_MODE, 0, -1, "¥", 0, 0, "40 2C 2A 50 EC 11 EC 11 EC", "B2 (UTF-8)" }, + /* 34*/ { UNICODE_MODE, 0, -1, "・", 0, 0, "40 1A 50 EC 11 EC 11 EC 11", "B1 (Shift JIS) single-byte codepoint A5 (same bytes as ¥ ISO 8859-1 above, so ambiguous)" }, + /* 35*/ { UNICODE_MODE, 3, -1, "・", ZINT_ERROR_INVALID_DATA, -1, "Error 575: Invalid characters in input data", "" }, + /* 36*/ { UNICODE_MODE, 20, -1, "・", 0, 20, "71 44 01 A5 00 EC 11 EC 11", "ECI-20 B1 (Shift JIS) single-byte codepoint A5" }, + /* 37*/ { UNICODE_MODE, 26, -1, "・", 0, 26, "71 A4 03 EF BD A5 00 EC 11", "ECI-26 B3 (UTF-8)" }, + /* 38*/ { DATA_MODE, 0, -1, "・", 0, 0, "40 3E FB DA 50 EC 11 EC 11", "B3 (UTF-8)" }, + /* 39*/ { UNICODE_MODE, 0, -1, "¿", 0, 0, "40 1B F0 EC 11 EC 11 EC 11", "B1 (ISO 8859-1) (same bytes as ソ Shift JIS below, so ambiguous)" }, + /* 40*/ { UNICODE_MODE, 3, -1, "¿", 0, 3, "70 34 01 BF 00 EC 11 EC 11", "ECI-3 B1 (ISO 8859-1)" }, + /* 41*/ { UNICODE_MODE, 20, -1, "¿", ZINT_ERROR_INVALID_DATA, -1, "Error 800: Invalid character in input data", "¿ not in Shift JIS" }, + /* 42*/ { UNICODE_MODE, 26, -1, "¿", 0, 26, "71 A4 02 C2 BF 00 EC 11 EC", "ECI-26 B2 (UTF-8)" }, + /* 43*/ { DATA_MODE, 0, -1, "¿", 0, 0, "40 2C 2B F0 EC 11 EC 11 EC", "B2 (UTF-8)" }, + /* 44*/ { UNICODE_MODE, 0, -1, "ソ", 0, 0, "40 1B F0 EC 11 EC 11 EC 11", "B1 (Shift JIS) single-byte codepoint BF (same bytes as ¿ ISO 8859-1 above, so ambiguous)" }, + /* 45*/ { UNICODE_MODE, 3, -1, "ソ", ZINT_ERROR_INVALID_DATA, -1, "Error 575: Invalid characters in input data", "" }, + /* 46*/ { UNICODE_MODE, 20, -1, "ソ", 0, 20, "71 44 01 BF 00 EC 11 EC 11", "ECI-20 B1 (Shift JIS) single-byte codepoint BF" }, + /* 47*/ { UNICODE_MODE, 26, -1, "ソ", 0, 26, "71 A4 03 EF BD BF 00 EC 11", "ECI-26 B3 (UTF-8)" }, + /* 48*/ { DATA_MODE, 0, -1, "ソ", 0, 0, "40 3E FB DB F0 EC 11 EC 11", "B3 (UTF-8)" }, + /* 49*/ { UNICODE_MODE, 0, -1, "~", 0, 0, "40 17 E0 EC 11 EC 11 EC 11", "B1 (ASCII) (same bytes as ‾ Shift JIS below, so ambiguous)" }, + /* 50*/ { UNICODE_MODE, 3, -1, "~", 0, 3, "70 34 01 7E 00 EC 11 EC 11", "ECI-3 B1 (ASCII)" }, + /* 51*/ { UNICODE_MODE, 20, -1, "~", ZINT_ERROR_INVALID_DATA, -1, "Error 800: Invalid character in input data", "tilde not in Shift JIS (codepoint used for overline)" }, + /* 52*/ { UNICODE_MODE, 0, -1, "‾", 0, 0, "40 17 E0 EC 11 EC 11 EC 11", "B1 (Shift JIS) single-byte codepoint 7E (same bytes as ~ ASCII above, so ambiguous)" }, + /* 53*/ { UNICODE_MODE, 3, -1, "‾", ZINT_ERROR_INVALID_DATA, -1, "Error 575: Invalid characters in input data", "" }, + /* 54*/ { UNICODE_MODE, 20, -1, "‾", 0, 20, "71 44 01 7E 00 EC 11 EC 11", "ECI-20 B1 (Shift JIS) (to single-byte tilde codepoint 7E, so byte mode)" }, + /* 55*/ { UNICODE_MODE, 26, -1, "‾", 0, 26, "71 A4 03 E2 80 BE 00 EC 11", "ECI-26 B3 (UTF-8)" }, + /* 56*/ { DATA_MODE, 0, -1, "‾", 0, 0, "40 3E 28 0B E0 EC 11 EC 11", "B3 (UTF-8)" }, + /* 57*/ { UNICODE_MODE, 0, -1, "点", 0, 0, "80 16 CF 80 EC 11 EC 11 EC", "K1 (Shift JIS)" }, + /* 58*/ { UNICODE_MODE, 3, -1, "点", ZINT_ERROR_INVALID_DATA, -1, "Error 575: Invalid characters in input data", "" }, + /* 59*/ { UNICODE_MODE, 20, -1, "点", 0, 20, "71 48 01 6C F8 00 EC 11 EC", "ECI-20 K1 (Shift JIS)" }, + /* 60*/ { UNICODE_MODE, 26, -1, "点", 0, 26, "71 A4 03 E7 82 B9 00 EC 11", "ECI-26 B3 (UTF-8)" }, + /* 61*/ { DATA_MODE, 0, -1, "点", 0, 0, "40 3E 78 2B 90 EC 11 EC 11", "B3 (UTF-8)" }, + /* 62*/ { DATA_MODE, 0, -1, "\223\137", 0, 0, "40 29 35 F0 EC 11 EC 11 EC", "B2 (Shift JIS) (not full multibyte)" }, + /* 63*/ { DATA_MODE, 0, 200, "\223\137", 0, 0, "80 16 CF 80 EC 11 EC 11 EC", "K1 (Shift JIS)" }, + /* 64*/ { UNICODE_MODE, 0, -1, "¥・点", 0, 0, "40 45 CA 59 35 F0 EC 11 EC", "B4 (Shift JIS) (optimized to byte mode only)" }, + /* 65*/ { UNICODE_MODE, 3, -1, "¥・点", ZINT_ERROR_INVALID_DATA, -1, "Error 575: Invalid characters in input data", "" }, + /* 66*/ { UNICODE_MODE, 20, -1, "¥・点", 0, 20, "71 44 04 5C A5 93 5F 00 EC", "ECI-20 B4 (Shift JIS)" }, + /* 67*/ { UNICODE_MODE, 26, -1, "¥・点", 0, 26, "71 A4 08 C2 A5 EF BD A5 E7 82 B9 00 EC", "ECI-26 B8 (UTF-8)" }, + /* 68*/ { DATA_MODE, 0, -1, "\134\245\223\137", 0, 0, "40 45 CA 59 35 F0 EC 11 EC", "B8 (Shift JIS)" }, + /* 69*/ { DATA_MODE, 0, -1, "¥・点", 0, 0, "40 8C 2A 5E FB DA 5E 78 2B 90 EC 11 EC", "B8 (UTF-8)" }, + /* 70*/ { UNICODE_MODE, 0, -1, "点茗", 0, 0, "80 26 CF EA A8 00 EC 11 EC", "K2 (Shift JIS)" }, + /* 71*/ { UNICODE_MODE, 0, -1, "点茗テ", 0, 0, "80 36 CF EA A8 34 A0 EC 11", "K3 (Shift JIS)" }, + /* 72*/ { UNICODE_MODE, 0, -1, "点茗テ点", 0, 0, "80 46 CF EA A8 34 AD 9F 00", "K4 (Shift JIS)" }, + /* 73*/ { UNICODE_MODE, 0, -1, "点茗テ点茗", 0, 0, "80 56 CF EA A8 34 AD 9F D5 50 00 EC 11", "K5 (Shift JIS)" }, + /* 74*/ { UNICODE_MODE, 0, -1, "点茗テ点茗テ", 0, 0, "80 66 CF EA A8 34 AD 9F D5 50 69 40 EC", "K6 (Shift JIS)" }, + /* 75*/ { UNICODE_MODE, 0, -1, "点茗テ点茗テソ", 0, 0, "80 66 CF EA A8 34 AD 9F D5 50 69 50 06 FC 00 EC", "K6 B1 (Shift JIS)" }, + /* 76*/ { DATA_MODE, 0, -1, "\223\137\344\252\203\145\223\137\344\252\203\145\277", 0, 0, "40 D9 35 FE 4A A8 36 59 35 FE 4A A8 36 5B F0 EC", "B13 (Shift JIS)" }, + /* 77*/ { DATA_MODE, 0, 200, "\223\137\344\252\203\145\223\137\344\252\203\145\277", 0, 0, "80 66 CF EA A8 34 AD 9F D5 50 69 50 06 FC 00 EC", "K6 B1 (Shift JIS) (full multibyte)" }, + /* 78*/ { DATA_MODE, 0, -1, "点茗テ点茗テソ", 0, 0, "41 5E 78 2B 9E 88 C9 7E 38 38 6E 78 2B 9E 88 C9 7E 38 38 6E FB DB F0 EC 11 EC 11 EC", "B21 (UTF-8)" }, + /* 79*/ { DATA_MODE, 0, -1, "ÁȁȁȁȁȁȁȂ¢", 0, 0, "41 2C 38 1C 88 1C 88 1C 88 1C 88 1C 88 1C 88 1C 88 2C 2A 20 EC 11", "B18 (UTF-8)" }, + /* 80*/ { DATA_MODE, 0, 200, "ÁȁȁȁȁȁȁȂ¢", 0, 0, "41 2C 38 1C 88 1C 88 1C 88 1C 88 1C 88 1C 88 1C 88 2C 2A 20 EC 11", "B18 (UTF-8) (full multibyte)" }, + /* 81*/ { DATA_MODE, 0, -1, "ÁȁȁȁȁȁȁȁȂ¢", 0, 0, "41 4C 38 1C 88 1C 88 1C 88 1C 88 1C 88 1C 88 1C 88 1C 88 2C 2A 20", "B20 (UTF-8)" }, + /* 82*/ { DATA_MODE, 0, 200, "ÁȁȁȁȁȁȁȁȂ¢", 0, 0, "40 1C 38 09 04 40 22 01 10 08 80 44 02 20 11 00 88 0A 12 00 D1 00", "B1 K9 B1 (UTF-8) (full multibyte)" }, + /* 83*/ { UNICODE_MODE, 0, -1, "ÁȁȁȁȁȁȁȂ¢", ZINT_WARN_USES_ECI, 26, "Warning 71 A4 12 C3 81 C8 81 C8 81 C8 81 C8 81 C8 81 C8 81 C8 82 C2 A2 00", "B18 (UTF-8)" }, + /* 84*/ { UNICODE_MODE, 0, 200, "ÁȁȁȁȁȁȁȂ¢", ZINT_WARN_USES_ECI, 26, "Warning 71 A4 12 C3 81 C8 81 C8 81 C8 81 C8 81 C8 81 C8 81 C8 82 C2 A2 00", "B18 (UTF-8)" }, + /* 85*/ { UNICODE_MODE, 0, -1, "ÁȁȁȁȁȁȁȁȂ¢", ZINT_WARN_USES_ECI, 26, "Warning 71 A4 14 C3 81 C8 81 C8 81 C8 81 C8 81 C8 81 C8 81 C8 81 C8 82 C2 A2 00 EC 11 EC 11", "B20 (UTF-8)" }, + /* 86*/ { UNICODE_MODE, 0, 200, "ÁȁȁȁȁȁȁȁȂ¢", ZINT_WARN_USES_ECI, 26, "Warning 71 A4 01 C3 80 90 44 02 20 11 00 88 04 40 22 01 10 08 80 A1 20 0D 10 00 EC 11 EC 11", "B1 K9 B1 (UTF-8) (full multibyte)" }, + /* 87*/ { UNICODE_MODE, 0, -1, "áA", 0, 0, "40 2E 14 10 EC 11 EC 11 EC", "B2 (ISO 8859-1)" }, + /* 88*/ { UNICODE_MODE, 0, 200, "áA", 0, 0, "80 1C 00 80 EC 11 EC 11 EC", "K1 (ISO 8859-1) (full multibyte)" }, }; int data_size = sizeof(data) / sizeof(struct item); @@ -250,6 +264,9 @@ static void test_qr_input(void) symbol->symbology = BARCODE_QRCODE; symbol->input_mode = data[i].input_mode; symbol->eci = data[i].eci; + if (data[i].option_3 != -1) { + symbol->option_3 = data[i].option_3; + } symbol->debug = ZINT_DEBUG_TEST; // Needed to get codeword dump in errtxt int length = strlen(data[i].data); @@ -258,9 +275,9 @@ static void test_qr_input(void) assert_equal(ret, data[i].ret, "i:%d ZBarcode_Encode ret %d != %d\n", i, ret, data[i].ret); #ifdef TEST_QR_INPUT_GENERATE_EXPECTED - printf(" /*%3d*/ { %s, %d, \"%s\", %s, %d, \"%s\", \"%s\" },\n", - i, testUtilInputModeName(data[i].input_mode), data[i].eci, testUtilEscape(data[i].data, length, escaped, sizeof(escaped)), testUtilErrorName(data[i].ret), - ret < 5 ? symbol->eci : -1, symbol->errtxt, data[i].comment); + printf(" /*%3d*/ { %s, %d, %d, \"%s\", %s, %d, \"%s\", \"%s\" },\n", + i, testUtilInputModeName(data[i].input_mode), data[i].eci, data[i].option_3, testUtilEscape(data[i].data, length, escaped, sizeof(escaped)), + testUtilErrorName(data[i].ret), ret < 5 ? symbol->eci : -1, symbol->errtxt, data[i].comment); #else if (ret < 5) { @@ -391,6 +408,7 @@ static void test_qr_optimize(void) if (data[i].option_1 != -1) { symbol->option_1 = data[i].option_1; } + symbol->option_3 = ZINT_FULL_MULTIBYTE; symbol->debug = ZINT_DEBUG_TEST; int length = strlen(data[i].data); @@ -1028,6 +1046,7 @@ static void test_microqr_input(void) int ret; struct item { int input_mode; + int option_3; unsigned char* data; int ret; char* expected; @@ -1045,38 +1064,49 @@ static void test_microqr_input(void) // ‾ U+203E overline, not in ISO/Win, in Shift JIS single-byte 0x7E (\176) (tilde), UTF-8 E280BE // 点 U+70B9 kanji, in Shift JIS 0x935F (\223\137), UTF-8 E782B9 // 茗 U+8317 kanji, in Shift JIS 0xE4AA (\344\252), UTF-8 E88C97 + // Á U+00C1, UTF-8 C381; ȁ U+0201, UTF-8 C881; Ȃ U+0202, UTF-8 C882; ¢ U+00A2, UTF-8 C2A2; á U+00E1, UTF-8 C3A1 struct item data[] = { - /* 0*/ { UNICODE_MODE, "é", 0, "87 A4 00 EC 11 EC 11 EC 00", "B1 (ISO 8859-1)" }, - /* 1*/ { DATA_MODE, "é", 0, "8B 0E A4 00 EC 11 EC 11 00", "B2 (UTF-8)" }, - /* 2*/ { UNICODE_MODE, "β", 0, "C8 80 00 00 EC 11 EC 11 00", "K1 (Shift JIS)" }, - /* 3*/ { UNICODE_MODE, "ก", ZINT_ERROR_INVALID_DATA, "Error 800: Invalid character in input data", "ก not in Shift JIS" }, - /* 4*/ { UNICODE_MODE, "Ж", 0, "C8 91 C0 00 EC 11 EC 11 00", "K1 (Shift JIS)" }, - /* 5*/ { UNICODE_MODE, "ກ", ZINT_ERROR_INVALID_DATA, "Error 800: Invalid character in input data", "ກ not in Shift JIS" }, - /* 6*/ { UNICODE_MODE, "\\", 0, "85 70 00 EC 11 EC 11 EC 00", "B1 (ASCII)" }, - /* 7*/ { UNICODE_MODE, "¥", 0, "86 94 00 EC 11 EC 11 EC 00", "B1 (ISO 8859-1) (same bytes as ・ Shift JIS below, so ambiguous)" }, - /* 8*/ { UNICODE_MODE, "・", 0, "86 94 00 EC 11 EC 11 EC 00", "B1 (Shift JIS) single-byte codepoint A5 (same bytes as ¥ ISO 8859-1 above, so ambiguous)" }, - /* 9*/ { UNICODE_MODE, "¿", 0, "86 FC 00 EC 11 EC 11 EC 00", "B1 (ISO 8859-1) (same bytes as ソ Shift JIS below, so ambiguous)" }, - /* 10*/ { UNICODE_MODE, "ソ", 0, "86 FC 00 EC 11 EC 11 EC 00", "B1 (Shift JIS) (same bytes as ¿ ISO 8859-1 above, so ambiguous)" }, - /* 11*/ { UNICODE_MODE, "~", 0, "85 F8 00 EC 11 EC 11 EC 00", "B1 (ASCII) (same bytes as ‾ Shift JIS below, so ambiguous)" }, - /* 12*/ { UNICODE_MODE, "‾", 0, "85 F8 00 EC 11 EC 11 EC 00", "B1 (Shift JIS) (same bytes as ~ ASCII above, so ambiguous)" }, - /* 13*/ { UNICODE_MODE, "点", 0, "CB 67 C0 00 EC 11 EC 11 00", "K1 (Shift JIS)" }, - /* 14*/ { DATA_MODE, "\223\137", 0, "CB 67 C0 00 EC 11 EC 11 00", "K1 (Shift JIS)" }, - /* 15*/ { DATA_MODE, "点", 0, "8F 9E 0A E4 00 EC 11 EC 00", "B3 (UTF-8)" }, - /* 16*/ { UNICODE_MODE, "茗", 0, "CE AA 80 00 EC 11 EC 11 00", "K1 (Shift JIS)" }, - /* 17*/ { DATA_MODE, "\344\252", 0, "CE AA 80 00 EC 11 EC 11 00", "K1 (Shift JIS)" }, - /* 18*/ { DATA_MODE, "茗", 0, "8F A2 32 5C 00 EC 11 EC 00", "B3 (UTF-8)" }, - /* 19*/ { UNICODE_MODE, "¥点", 0, "8D 72 4D 7C 00 EC 11 EC 00", "B3 (Shift JIS) (optimized from B1 K1)" }, - /* 20*/ { DATA_MODE, "\134\223\137", 0, "8D 72 4D 7C 00 EC 11 EC 00", "B3 (Shift JIS) (optimized from B1 K1)" }, - /* 21*/ { DATA_MODE, "¥点", 0, "97 0A 97 9E 0A E4 00 EC 00", "B5 (UTF-8)" }, - /* 22*/ { UNICODE_MODE, "点茗", 0, "D3 67 F5 54 00 EC 11 EC 00", "K2 (Shift JIS)" }, - /* 23*/ { DATA_MODE, "\223\137\344\252", 0, "D3 67 F5 54 00 EC 11 EC 00", "K2 (Shift JIS)" }, - /* 24*/ { DATA_MODE, "点茗", 0, "9B 9E 0A E7 A2 32 5C 00 00", "B6 (UTF-8)" }, - /* 25*/ { UNICODE_MODE, "点茗・", 0, "D3 67 F5 55 0D 28 00 EC 00", "K2 B1 (Shift JIS)" }, - /* 26*/ { DATA_MODE, "\223\137\344\252\245", 0, "D3 67 F5 55 0D 28 00 EC 00", "K2 B1 (Shift JIS)" }, - /* 27*/ { DATA_MODE, "点茗・", 0, "A7 9E 0A E7 A2 32 5F BE F6 94 00", "B9 (UTF-8)" }, - /* 28*/ { UNICODE_MODE, "¥点茗・", 0, "99 72 4D 7F 92 AA 94 00 00", "B6 (Shift JIS) (optimized from B1 K2 B1)" }, - /* 29*/ { DATA_MODE, "\134\223\137\344\252\245", 0, "99 72 4D 7F 92 AA 94 00 00", "B6 (Shift JIS) (optimized from B1 K2 B1)" }, - /* 30*/ { DATA_MODE, "¥点茗・", 0, "4B C2 A5 E7 82 B9 E8 8C 97 EF BD A5 00 00", "B11 (UTF-8)" }, + /* 0*/ { UNICODE_MODE, -1, "é", 0, "87 A4 00 EC 11 EC 11 EC 00", "B1 (ISO 8859-1)" }, + /* 1*/ { DATA_MODE, -1, "é", 0, "8B 0E A4 00 EC 11 EC 11 00", "B2 (UTF-8)" }, + /* 2*/ { UNICODE_MODE, -1, "β", 0, "C8 80 00 00 EC 11 EC 11 00", "K1 (Shift JIS)" }, + /* 3*/ { UNICODE_MODE, -1, "ก", ZINT_ERROR_INVALID_DATA, "Error 800: Invalid character in input data", "ก not in Shift JIS" }, + /* 4*/ { UNICODE_MODE, -1, "Ж", 0, "C8 91 C0 00 EC 11 EC 11 00", "K1 (Shift JIS)" }, + /* 5*/ { UNICODE_MODE, -1, "ກ", ZINT_ERROR_INVALID_DATA, "Error 800: Invalid character in input data", "ກ not in Shift JIS" }, + /* 6*/ { UNICODE_MODE, -1, "\\", 0, "85 70 00 EC 11 EC 11 EC 00", "B1 (ASCII)" }, + /* 7*/ { UNICODE_MODE, -1, "¥", 0, "86 94 00 EC 11 EC 11 EC 00", "B1 (ISO 8859-1) (same bytes as ・ Shift JIS below, so ambiguous)" }, + /* 8*/ { UNICODE_MODE, -1, "・", 0, "86 94 00 EC 11 EC 11 EC 00", "B1 (Shift JIS) single-byte codepoint A5 (same bytes as ¥ ISO 8859-1 above, so ambiguous)" }, + /* 9*/ { UNICODE_MODE, -1, "¿", 0, "86 FC 00 EC 11 EC 11 EC 00", "B1 (ISO 8859-1) (same bytes as ソ Shift JIS below, so ambiguous)" }, + /* 10*/ { UNICODE_MODE, -1, "ソ", 0, "86 FC 00 EC 11 EC 11 EC 00", "B1 (Shift JIS) (same bytes as ¿ ISO 8859-1 above, so ambiguous)" }, + /* 11*/ { UNICODE_MODE, -1, "~", 0, "85 F8 00 EC 11 EC 11 EC 00", "B1 (ASCII) (same bytes as ‾ Shift JIS below, so ambiguous)" }, + /* 12*/ { UNICODE_MODE, -1, "‾", 0, "85 F8 00 EC 11 EC 11 EC 00", "B1 (Shift JIS) (same bytes as ~ ASCII above, so ambiguous)" }, + /* 13*/ { UNICODE_MODE, -1, "点", 0, "CB 67 C0 00 EC 11 EC 11 00", "K1 (Shift JIS)" }, + /* 14*/ { DATA_MODE, -1, "\223\137", 0, "8A 4D 7C 00 EC 11 EC 11 00", "B2 (Shift JIS)" }, + /* 15*/ { DATA_MODE, 200, "\223\137", 0, "CB 67 C0 00 EC 11 EC 11 00", "K1 (Shift JIS) (full multibyte)" }, + /* 16*/ { DATA_MODE, -1, "点", 0, "8F 9E 0A E4 00 EC 11 EC 00", "B3 (UTF-8)" }, + /* 17*/ { UNICODE_MODE, -1, "茗", 0, "CE AA 80 00 EC 11 EC 11 00", "K1 (Shift JIS)" }, + /* 18*/ { DATA_MODE, -1, "\344\252", 0, "8B 92 A8 00 EC 11 EC 11 00", "B2 (Shift JIS)" }, + /* 19*/ { DATA_MODE, 200, "\344\252", 0, "CE AA 80 00 EC 11 EC 11 00", "K1 (Shift JIS) (full multibyte)" }, + /* 20*/ { DATA_MODE, -1, "茗", 0, "8F A2 32 5C 00 EC 11 EC 00", "B3 (UTF-8)" }, + /* 21*/ { UNICODE_MODE, -1, "¥点", 0, "8D 72 4D 7C 00 EC 11 EC 00", "B3 (Shift JIS) (optimized from B1 K1)" }, + /* 22*/ { DATA_MODE, -1, "\134\223\137", 0, "8D 72 4D 7C 00 EC 11 EC 00", "B3 (Shift JIS) (optimized from B1 K1)" }, + /* 23*/ { DATA_MODE, -1, "¥点", 0, "97 0A 97 9E 0A E4 00 EC 00", "B5 (UTF-8)" }, + /* 24*/ { UNICODE_MODE, -1, "点茗", 0, "D3 67 F5 54 00 EC 11 EC 00", "K2 (Shift JIS)" }, + /* 25*/ { DATA_MODE, -1, "\223\137\344\252", 0, "92 4D 7F 92 A8 00 EC 11 00", "B4 (Shift JIS)" }, + /* 26*/ { DATA_MODE, 200, "\223\137\344\252", 0, "D3 67 F5 54 00 EC 11 EC 00", "K2 (Shift JIS) (full multibyte)" }, + /* 27*/ { DATA_MODE, -1, "点茗", 0, "9B 9E 0A E7 A2 32 5C 00 00", "B6 (UTF-8)" }, + /* 28*/ { DATA_MODE, 200, "点茗", 0, "9B 9E 0A E7 A2 32 5C 00 00", "B6 (UTF-8)" }, + /* 29*/ { UNICODE_MODE, -1, "点茗・", 0, "D3 67 F5 55 0D 28 00 EC 00", "K2 B1 (Shift JIS)" }, + /* 30*/ { DATA_MODE, -1, "\223\137\344\252\245", 0, "96 4D 7F 92 AA 94 00 EC 00", "B5 (Shift JIS)" }, + /* 31*/ { DATA_MODE, 200, "\223\137\344\252\245", 0, "D3 67 F5 55 0D 28 00 EC 00", "K2 B1 (Shift JIS) (full multibyte)" }, + /* 32*/ { DATA_MODE, -1, "点茗・", 0, "A7 9E 0A E7 A2 32 5F BE F6 94 00", "B9 (UTF-8)" }, + /* 33*/ { UNICODE_MODE, -1, "¥点茗・", 0, "99 72 4D 7F 92 AA 94 00 00", "B6 (Shift JIS) (optimized from B1 K2 B1)" }, + /* 34*/ { DATA_MODE, -1, "\134\223\137\344\252\245", 0, "99 72 4D 7F 92 AA 94 00 00", "B6 (Shift JIS) (optimized from B1 K2 B1)" }, + /* 35*/ { DATA_MODE, -1, "¥点茗・", 0, "4B C2 A5 E7 82 B9 E8 8C 97 EF BD A5 00 00", "B11 (UTF-8)" }, + /* 36*/ { DATA_MODE, -1, "ÁȁȁȁȂ¢", 0, "4C C3 81 C8 81 C8 81 C8 81 C8 82 C2 A2 00", "B12 (UTF-8)" }, + /* 37*/ { DATA_MODE, -1, "ÁȁȁȁȁȂ¢", 0, "4E C3 81 C8 81 C8 81 C8 81 C8 81 C8 82 C2 A2 00", "B14 (UTF-8)" }, + /* 38*/ { DATA_MODE, 200, "ÁȁȁȁȁȂ¢", 0, "41 C3 6C 08 80 44 02 20 11 00 88 0A 12 0D 10 00", "B1 K6 B1 (UTF-8) (full multibyte)" }, + /* 39*/ { UNICODE_MODE, -1, "áA", 0, "8B 85 04 00 EC 11 EC 11 00", "B2 (ISO 8859-1)" }, + /* 40*/ { UNICODE_MODE, 200, "áA", 0, "CE 00 40 00 EC 11 EC 11 00", "K1 (ISO 8859-1) (full multibyte)" }, }; int data_size = sizeof(data) / sizeof(struct item); @@ -1089,6 +1119,9 @@ static void test_microqr_input(void) symbol->symbology = BARCODE_MICROQR; symbol->input_mode = data[i].input_mode; + if (data[i].option_3 != -1) { + symbol->option_3 = data[i].option_3; + } symbol->debug = ZINT_DEBUG_TEST; // Needed to get codeword dump in errtxt int length = strlen(data[i].data); @@ -1097,9 +1130,9 @@ static void test_microqr_input(void) assert_equal(ret, data[i].ret, "i:%d ZBarcode_Encode ret %d != %d\n", i, ret, data[i].ret); #ifdef TEST_MICROQR_INPUT_GENERATE_EXPECTED - printf(" /*%3d*/ { %s, \"%s\", %s, \"%s\", \"%s\" },\n", - i, testUtilInputModeName(data[i].input_mode), testUtilEscape(data[i].data, length, escaped, sizeof(escaped)), testUtilErrorName(data[i].ret), - symbol->errtxt, data[i].comment); + printf(" /*%3d*/ { %s, %d, \"%s\", %s, \"%s\", \"%s\" },\n", + i, testUtilInputModeName(data[i].input_mode), data[i].option_3, testUtilEscape(data[i].data, length, escaped, sizeof(escaped)), + testUtilErrorName(data[i].ret), symbol->errtxt, data[i].comment); #else if (ret < 5) { assert_zero(strcmp(symbol->errtxt, data[i].expected), "i:%d strcmp(%s, %s) != 0\n", i, symbol->errtxt, data[i].expected); @@ -1232,6 +1265,7 @@ static void test_microqr_optimize(void) if (data[i].option_2 != -1) { symbol->option_2 = data[i].option_2; } + symbol->option_3 = ZINT_FULL_MULTIBYTE; symbol->debug = ZINT_DEBUG_TEST; int length = strlen(data[i].data); @@ -1795,6 +1829,7 @@ static void test_rmqr_input(void) int ret; struct item { int input_mode; + int option_3; unsigned char* data; int ret; char* expected; @@ -1806,21 +1841,21 @@ static void test_rmqr_input(void) // Ж U+0416 in ISO 8859-5 Cyrillic (but not other ISO 8859), Win 1251, in Shift JIS 0x8447, UTF-8 D096 // ກ U+0E81 Lao not in any ISO 8859 (or Win page) or Shift JIS, UTF-8 E0BA81 // ¥ U+00A5 in ISO 8859-1 0xA5 (\245), in Shift JIS single-byte 0x5C (\134) (backslash); 0xA5 same codepoint as single-byte half-width katakana ・ (U+FF65) in Shift JIS (below), UTF-8 C2A5 - // ・ U+FF65 half-width katakana, not in ISO/Win, in Shift JIS single-byte 0xA5 (\245), UTF-8 EFBDA5 - // ¿ U+00BF in ISO 8859-1 0xBF (\277), not in Shift JIS; 0xBF same codepoint as single-byte half-width katakana ソ (U+FF7F) in Shift JIS (below), UTF-8 C2BF - // ソ U+FF7F half-width katakana, not in ISO/Win, in Shift JIS single-byte 0xBF (\277), UTF-8 EFBDBF - // ‾ U+203E overline, not in ISO/Win, in Shift JIS single-byte 0x7E (\176) (tilde), UTF-8 E280BE // 点 U+70B9 kanji, in Shift JIS 0x935F (\223\137), UTF-8 E782B9 - // 茗 U+8317 kanji, in Shift JIS 0xE4AA (\344\252), UTF-8 E88C97 - // テ U+30C6 katakana, in Shift JIS 0x8365 (\203\145), UTF-8 E38386 + // Á U+00C1, UTF-8 C381; ȁ U+0201, UTF-8 C881; Ȃ U+0202, UTF-8 C882; ¢ U+00A2, UTF-8 C2A2 struct item data[] = { - /* 0*/ { UNICODE_MODE, "é", 0, "67 A4 00 EC 11", "B1 (ISO 8859-1)" }, - /* 1*/ { DATA_MODE, "é", 0, "6B 0E A4 00 EC", "B2 (UTF-8)" }, - /* 2*/ { DATA_MODE, "\351", 0, "67 A4 00 EC 11", "B1 (ISO 8859-1)" }, - /* 3*/ { UNICODE_MODE, "β", 0, "88 80 00 EC 11", "K1 (Shift JIS)" }, - /* 4*/ { UNICODE_MODE, "ก", ZINT_ERROR_INVALID_DATA, "Error 800: Invalid character in input data", "ก not in ISO 8859-1 or Shift JIS" }, - /* 5*/ { UNICODE_MODE, "Ж", 0, "88 91 C0 EC 11", "K1 (Shift JIS)" }, - /* 6*/ { UNICODE_MODE, "¥・点", 0, "71 72 96 4D 7C", "B2 K1 (Shift JIS) (optimized to byte mode only)" }, + /* 0*/ { UNICODE_MODE, -1, "é", 0, "67 A4 00 EC 11", "B1 (ISO 8859-1)" }, + /* 1*/ { DATA_MODE, -1, "é", 0, "6B 0E A4 00 EC", "B2 (UTF-8)" }, + /* 2*/ { DATA_MODE, -1, "\351", 0, "67 A4 00 EC 11", "B1 (ISO 8859-1)" }, + /* 3*/ { UNICODE_MODE, -1, "β", 0, "88 80 00 EC 11", "K1 (Shift JIS)" }, + /* 4*/ { UNICODE_MODE, -1, "ก", ZINT_ERROR_INVALID_DATA, "Error 800: Invalid character in input data", "ก not in ISO 8859-1 or Shift JIS" }, + /* 5*/ { UNICODE_MODE, -1, "Ж", 0, "88 91 C0 EC 11", "K1 (Shift JIS)" }, + /* 6*/ { UNICODE_MODE, -1, "¥・点", 0, "71 72 96 4D 7C", "B2 K1 (Shift JIS) (optimized to byte mode only)" }, + /* 7*/ { DATA_MODE, -1, "ÁȁȁȁȂ¢", 0, "6C C3 81 C8 81 C8 81 C8 81 C8 82 C2 A2 00 EC 11 EC 11 EC", "B12 (UTF-8)" }, + /* 8*/ { DATA_MODE, -1, "ÁȁȁȁȁȂ¢", 0, "6E C3 81 C8 81 C8 81 C8 81 C8 81 C8 82 C2 A2 00 EC 11 EC", "B14 (UTF-8)" }, + /* 9*/ { DATA_MODE, 200, "ÁȁȁȁȁȂ¢", 0, "61 C3 8C 08 80 44 02 20 11 00 88 0A 13 0D 10 EC 11 EC 11", "B1 K6 B1 (UTF-8) (full multibyte)" }, + /* 10*/ { UNICODE_MODE, -1, "áA", 0, "6B 85 04 00 EC", "B2 (ISO 8859-1)" }, + /* 11*/ { UNICODE_MODE, 200, "áA", 0, "8E 00 40 EC 11", "K1 (ISO 8859-1) (full multibyte)" }, }; int data_size = sizeof(data) / sizeof(struct item); @@ -1833,6 +1868,9 @@ static void test_rmqr_input(void) symbol->symbology = BARCODE_RMQR; symbol->input_mode = data[i].input_mode; + if (data[i].option_3 != -1) { + symbol->option_3 = data[i].option_3; + } symbol->debug = ZINT_DEBUG_TEST; // Needed to get codeword dump in errtxt int length = strlen(data[i].data); @@ -1841,9 +1879,9 @@ static void test_rmqr_input(void) assert_equal(ret, data[i].ret, "i:%d ZBarcode_Encode ret %d != %d\n", i, ret, data[i].ret); #ifdef TEST_RMQR_INPUT_GENERATE_EXPECTED - printf(" /*%3d*/ { %s, \"%s\", %s, \"%s\", \"%s\" },\n", - i, testUtilInputModeName(data[i].input_mode), testUtilEscape(data[i].data, length, escaped, sizeof(escaped)), testUtilErrorName(data[i].ret), - symbol->errtxt, data[i].comment); + printf(" /*%3d*/ { %s, %d, \"%s\", %s, \"%s\", \"%s\" },\n", + i, testUtilInputModeName(data[i].input_mode), data[i].option_3, testUtilEscape(data[i].data, length, escaped, sizeof(escaped)), + testUtilErrorName(data[i].ret), symbol->errtxt, data[i].comment); #else if (ret < 5) { assert_zero(strcmp(symbol->errtxt, data[i].expected), "i:%d strcmp(%s, %s) != 0\n", i, symbol->errtxt, data[i].expected); @@ -1965,6 +2003,7 @@ static void test_rmqr_optimize(void) if (data[i].option_1 != -1) { symbol->option_1 = data[i].option_1; } + symbol->option_3 = ZINT_FULL_MULTIBYTE; symbol->debug = ZINT_DEBUG_TEST; int length = strlen(data[i].data); diff --git a/backend/tests/test_sjis.c b/backend/tests/test_sjis.c index 53f77c4b..d78be088 100644 --- a/backend/tests/test_sjis.c +++ b/backend/tests/test_sjis.c @@ -170,6 +170,7 @@ static void test_sjis_utf8tosb(void) int ret; struct item { int eci; + int full_multibyte; unsigned char* data; int length; int ret; @@ -188,13 +189,20 @@ static void test_sjis_utf8tosb(void) // À U+00C0 in ISO 8859-1 0xC0, outside first byte range and 0xEBxx second byte range // s/\/\*[ 0-9]*\*\//\=printf("\/*%3d*\/", line(".") - line("'<")) struct item data[] = { - /* 0*/ { 3, "é", -1, 0, 1, { 0xE9 }, "" }, - /* 1*/ { 3, "β", -1, ZINT_ERROR_INVALID_DATA, -1, {}, "" }, - /* 2*/ { 9, "β", -1, 0, 1, { 0xE2 }, "" }, - /* 3*/ { 3, "¥", -1, 0, 1, { 0xA5 }, "" }, - /* 4*/ { 3, "éa", -1, 0, 1, { 0xE961 }, "In QR Kanji mode range" }, - /* 5*/ { 3, "éaúbàcëdìeµ", -1, 0, 8, { 0xE961, 0xFA, 0x62, 0xE063, 0xEB64, 0xEC, 0x65, 0xB5 }, "" }, - /* 6*/ { 3, "ëÀ", -1, 0, 2, { 0xEB, 0xC0 }, "Outside QR Kanji mode range" }, + /* 0*/ { 3, 0, "é", -1, 0, 1, { 0xE9 }, "" }, + /* 1*/ { 3, 1, "é", -1, 0, 1, { 0xE9 }, "" }, + /* 2*/ { 3, 0, "β", -1, ZINT_ERROR_INVALID_DATA, -1, {}, "" }, + /* 3*/ { 3, 1, "β", -1, ZINT_ERROR_INVALID_DATA, -1, {}, "" }, + /* 4*/ { 9, 0, "β", -1, 0, 1, { 0xE2 }, "" }, + /* 5*/ { 9, 1, "β", -1, 0, 1, { 0xE2 }, "" }, + /* 6*/ { 3, 0, "¥", -1, 0, 1, { 0xA5 }, "" }, + /* 7*/ { 3, 1, "¥", -1, 0, 1, { 0xA5 }, "" }, + /* 8*/ { 3, 0, "éa", -1, 0, 2, { 0xE9, 0x61 }, "Not full multibyte" }, + /* 9*/ { 3, 1, "éa", -1, 0, 1, { 0xE961 }, "In QR Kanji mode range" }, + /* 10*/ { 3, 0, "éaúbàcëdìeµ", -1, 0, 11, { 0xE9, 0x61, 0xFA, 0x62, 0xE0, 0x63, 0xEB, 0x64, 0xEC, 0x65, 0xB5 }, "" }, + /* 11*/ { 3, 1, "éaúbàcëdìeµ", -1, 0, 8, { 0xE961, 0xFA, 0x62, 0xE063, 0xEB64, 0xEC, 0x65, 0xB5 }, "" }, + /* 12*/ { 3, 0, "ëÀ", -1, 0, 2, { 0xEB, 0xC0 }, "Not full multibyte" }, + /* 13*/ { 3, 1, "ëÀ", -1, 0, 2, { 0xEB, 0xC0 }, "Outside QR Kanji mode range" }, }; int data_size = sizeof(data) / sizeof(struct item); @@ -206,7 +214,7 @@ static void test_sjis_utf8tosb(void) int length = data[i].length == -1 ? strlen(data[i].data) : data[i].length; size_t ret_length = length; - ret = sjis_utf8tosb(data[i].eci, data[i].data, &ret_length, jisdata); + ret = sjis_utf8tosb(data[i].eci, data[i].data, &ret_length, jisdata, data[i].full_multibyte); assert_equal(ret, data[i].ret, "i:%d ret %d != %d\n", i, ret, data[i].ret); if (ret == 0) { assert_equal(ret_length, data[i].ret_length, "i:%d ret_length %zu != %zu\n", i, ret_length, data[i].ret_length); @@ -225,6 +233,7 @@ static void test_sjis_cpy(void) int ret; struct item { + int full_multibyte; unsigned char* data; int length; int ret; @@ -234,11 +243,15 @@ static void test_sjis_cpy(void) }; // s/\/\*[ 0-9]*\*\//\=printf("\/*%3d*\/", line(".") - line("'<")) struct item data[] = { - /* 0*/ { "\351", -1, 0, 1, { 0xE9 }, "In QR Kanji mode first-byte range but only one byte" }, - /* 1*/ { "\351\141", -1, 0, 1, { 0xE961 }, "In QR Kanji mode range" }, - /* 2*/ { "\201", -1, 0, 1, { 0x81 }, "In QR Kanji mode first-byte range but only one byte" }, - /* 3*/ { "\201\141", -1, 0, 1, { 0x8161 }, "In QR Kanji mode range" }, - /* 4*/ { "\201\077\201\100\237\374\237\375\340\077\340\100\353\277\353\300", -1, 0, 12, { 0x81, 0x3F, 0x8140, 0x9FFC, 0x9F, 0xFD, 0xE0, 0x3F, 0xE040, 0xEBBF, 0xEB, 0xC0 }, "" }, + /* 0*/ { 0, "\351", -1, 0, 1, { 0xE9 }, "Not full multibyte" }, + /* 1*/ { 1, "\351", -1, 0, 1, { 0xE9 }, "In QR Kanji mode first-byte range but only one byte" }, + /* 2*/ { 0, "\351\141", -1, 0, 2, { 0xE9, 0x61 }, "Not full multibyte" }, + /* 3*/ { 1, "\351\141", -1, 0, 1, { 0xE961 }, "In QR Kanji mode range" }, + /* 4*/ { 1, "\201", -1, 0, 1, { 0x81 }, "In QR Kanji mode first-byte range but only one byte" }, + /* 5*/ { 0, "\201\141", -1, 0, 2, { 0x81, 0x61 }, "Not full multibyte" }, + /* 6*/ { 1, "\201\141", -1, 0, 1, { 0x8161 }, "In QR Kanji mode range" }, + /* 7*/ { 0, "\201\077\201\100\237\374\237\375\340\077\340\100\353\277\353\300", -1, 0, 16, { 0x81, 0x3F, 0x81, 0x40, 0x9F, 0xFC, 0x9F, 0xFD, 0xE0, 0x3F, 0xE0, 0x40, 0xEB, 0xBF, 0xEB, 0xC0 }, "" }, + /* 8*/ { 1, "\201\077\201\100\237\374\237\375\340\077\340\100\353\277\353\300", -1, 0, 12, { 0x81, 0x3F, 0x8140, 0x9FFC, 0x9F, 0xFD, 0xE0, 0x3F, 0xE040, 0xEBBF, 0xEB, 0xC0 }, "" }, }; int data_size = sizeof(data) / sizeof(struct item); @@ -250,7 +263,7 @@ static void test_sjis_cpy(void) int length = data[i].length == -1 ? strlen(data[i].data) : data[i].length; size_t ret_length = length; - sjis_cpy(data[i].data, &ret_length, jisdata); + sjis_cpy(data[i].data, &ret_length, jisdata, data[i].full_multibyte); assert_equal(ret_length, data[i].ret_length, "i:%d ret_length %zu != %zu\n", i, ret_length, data[i].ret_length); for (int j = 0; j < ret_length; j++) { assert_equal(jisdata[j], data[i].expected_jisdata[j], "i:%d jisdata[%d] %04X != %04X\n", i, j, jisdata[j], data[i].expected_jisdata[j]); diff --git a/backend/zint.h b/backend/zint.h index c51c7c67..de498d48 100644 --- a/backend/zint.h +++ b/backend/zint.h @@ -1,7 +1,7 @@ /* zint.h - definitions for libzint libzint - the open source barcode library - Copyright (C) 2009-2019 Robin Stuart + Copyright (C) 2009-2020 Robin Stuart Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions @@ -263,10 +263,13 @@ extern "C" { #define GS1_MODE 2 #define ESCAPE_MODE 8 -// Data Matrix specific options +// Data Matrix specific options (option_3) #define DM_SQUARE 100 #define DM_DMRE 101 +// QR, Han Xin, Grid Matrix specific options (option_3) +#define ZINT_FULL_MULTIBYTE 200 + // Warning and error conditions #define ZINT_WARN_INVALID_OPTION 2 #define ZINT_WARN_USES_ECI 3 diff --git a/docs/manual.txt b/docs/manual.txt index c3c7dc51..35cabb6e 100644 --- a/docs/manual.txt +++ b/docs/manual.txt @@ -218,9 +218,9 @@ For example: zint -o here.png -d "This Text" -This draws a Code 128 barcode in the file here.png. If an encapsulated Post Script -file is needed simply append the file name with .eps, and so on for the other -supported file types: +This draws a Code 128 barcode in the file here.png. If an encapsulated Post +Script file is needed simply append the file name with .eps, and so on for the +other supported file types: zint -o there.eps -d "This Text" @@ -377,8 +377,8 @@ gives an inverted Code 128 symbol. This is not practical for most symbologies but white-on-black is allowed by the Data Matrix and Aztec Code symbology specifications. -For more specific needs the foreground (ink) and background (paper) colours -can be specified using the --fg= and --bg= options followed by a number in RRGGBB +For more specific needs the foreground (ink) and background (paper) colours can +be specified using the --fg= and --bg= options followed by a number in RRGGBB hexadecimal notation (the same system used in HTML). For example the command zint --fg=004700 -d "This" @@ -407,16 +407,16 @@ example for PNG images a scale of 5 will increase the x-dimension to 10 pixels. By default all input data is assumed to be encoded in Unicode (UTF-8) format. Many barcode symbologies encode data using Latin-1 (ISO-8851-1) character encoding, so input is converted from Unicode to Latin-1 before being put in the -symbol. In addition QR Code, Micro QR Code, Han Xin Code and Grid Matrix -standards can encode Chinese or Japanese characters which are also converted -from Unicode. If Zint encounters characters which can not be encoded using the -default character encoding then it will take advantage of the ECI (Extended -Channel Interpretations) mechanism to encode the data. Be aware that not all -barcode readers support ECI mode, so this can sometimes lead to unreadable -barcodes. If you are using characters beyond those supported by Latin-1 then -you should check that the resulting barcode can be understood by your target -barcode reader. Zint will generate a warning message when ECI codes have been -inserted into a symbol. +symbol. In addition QR Code, Micro QR Code, Rectangular Micro QR Code, Han Xin +Code and Grid Matrix can encode Japanese or Chinese characters which are also +converted from Unicode. If Zint encounters characters which can not be encoded +using the default character encoding then it will take advantage of the ECI +(Extended Channel Interpretations) mechanism to encode the data. Be aware that +not all barcode readers support ECI mode, so this can sometimes lead to +unreadable barcodes. If you are using characters beyond those supported by +Latin-1 then you should check that the resulting barcode can be understood by +your target barcode reader. Zint will generate a warning message when ECI codes +have been inserted into a symbol. GS1 data can be encoded in a number of symbologies. Application identifiers should be enclosed in [square brackets] followed by the data to be encoded (see @@ -425,35 +425,47 @@ doesn't need to be set) for EAN-128, DataBar and Composite symbologies but is also available for Code 16k, Data Matrix, Aztec Code, DotCode and QR Code. HIBC data may also be encoded in the symbologies Code 39, Code128, Codablock-F, -Datamatrix, QR-Code, PDF417 and Aztec-Code. Within this mode, the leading '+' and the -check character is automatically added. +Data Matrix, QR Code, PDF417 and Aztec Code. Within this mode, the leading '+' +and the check character are automatically added. The --binary option prevents Zint from performing any convertion of the data before placing in the barcode symbol and should be used if you are encoding raw -binary or encrypted data. +binary or encrypted data. For an example involving QR Code and UTF-8 encoding, +see Ex3 below. -If your data contains non ISO-Latin-1 characters, you may encode it using an ECI-aware -Symbology and an ECI value from the table below. +The --fullmultibyte option uses the multibyte modes of QR Code, Micro QR Code, +Rectangular Micro QR Code, Han Xin Code and Grid Matrix for binary and Latin +data, maximizing density. You should check your barcode reader supports this use +before enabling it. + +If your data contains non ISO-Latin-1 characters, you may encode it using an +ECI-aware symbology and an ECI value from the table below. The ECI information is added to your code symbol as prefix data. -The ECI-Value may be specified with the --eci switch, followed by the value in the column -"ECI Code". -The ECI-Value of 0 does not encode any ECI-Information in the code symbol. In this case, -the default encoding applies for the data which is "ISO-8859-1 - Latin alphabet No. 1". +The ECI value may be specified with the --eci switch, followed by the value in +the column "ECI Code". +The ECI value of 0 does not encode any ECI information in the code symbol. In +this case, the default encoding applies for the data which is "ISO-8859-1 - +Latin alphabet No. 1". -The first row of the table (ECI code 3) is the default value and does not lead to any ECI -information included into the symbol. +The first row of the table (ECI code 3) is the default value and does not lead +to any ECI information being included in the symbol. -The input data should be utf-8 formatted. Zint automatically translates the data into the -target encoding. -The rows marked with a star (*) do not do this transformation. The data must be specified -as binary data (--binary switch) with the data in the encoding given by the "Character -Encoding Scheme" column. +The input data should be UTF-8 formatted. Zint automatically translates the +data into the target encoding. +The rows marked with a star (*) do not do this transformation. The data must be +specified as binary data (--binary switch) with the data in the encoding given +by the "Character Encoding Scheme" column. +The row marked with a double star (**) only does this transformation for QR +Code, Micro QR Code and Rectangular Micro QR Code. +The row marked with a triple star (***) only does this transformation for Han +Xin Code and Grid Matrix. Han Xin Code can encode GB 18030. Grid Matrix can +encode the subset GB 2312. -Note: the "--eci 3" specification may only be used for special purposes. Using this parameter, -the ECI information is explicitly added to the code symbol. Nevertheless, for ECI Code 3, this -is not required, as this is the default encoding, which is also active without any ECI -information. +Note: the "--eci 3" specification should only be used for special purposes. +Using this parameter, the ECI information is explicitly added to the code +symbol. Nevertheless, for ECI Code 3, this is not required, as this is the +default encoding, which is also active without any ECI information. -------------------------------------------------------- ECI Code | Character Encoding Scheme @@ -473,7 +485,7 @@ ECI Code | Character Encoding Scheme 16 | ISO-8859-14 - Latin alphabet No. 8 (Celtic) 17 | ISO-8859-15 - Latin alphabet No. 9 18 | ISO-8859-16 - Latin alphabet No. 10 -20 * | Shift-JIS (JISX 0208 amd JISX 0201) +20 ** | Shift-JIS (JISX 0208 amd JISX 0201) 21 | Windows-1250 - Latin 2 (Central Europe) 22 | Windows-1251 - Cyrillic 23 | Windows-1252 - Latin 1 @@ -482,24 +494,32 @@ ECI Code | Character Encoding Scheme 26 | Unicode (UTF-8) 27 | ISO-646:1991 7-bit character set 28 * | Big-5 (Taiwan) Chinese Character Set -29 * | GB (PRC) Chinese Character Set +29 *** | GB (PRC) Chinese Character Set 30 * | Korean Character Set (KSX1001:1998) -------------------------------------------------------- -Two examples: -Ex1: The Euro sign should be encoded in ISO-8859-15. +Three examples: +Ex1: The Euro sign can be encoded in ISO-8859-15. The Euro-Sign has the ISO8859-15 codepoint hex A4. It is encoded in utf-8 as the hex sequence: e2 82 ac Those 3 bytes are contained in the file "utf8euro.txt" This command will generate the corresponding code: + zint.exe -b 71 --square --scale 10 --eci 17 -i utf8euro.txt -Ex2: The Chinese character with Unicode codepoint hex 5e38 should be -encoded in big5 encoding. The big5 ECI is marked in the upper table to -require input data in big5 instead of utf-8. The big5 representation of -this character are the two hex bytes: 9c 75 (contained in the file big5char.txt). -The generation command is: -zint.exe -b 71 --square --scale 10 --eci 28 --binary -i big5char.txt +Ex2: The Chinese character with Unicode codepoint hex 5E38 can be encoded in +Big5 encoding. The Big5 ECI is marked in the upper table to require input data +in Big5 instead of UTF-8. The Big5 representation of this character is the two +hex bytes: 9C 75 (contained in the file big5char.txt). +The generation command for Data Matrix is: + +zint -b 71 --square --scale 10 --eci 28 --binary -i big5char.txt + +Ex3: Some decoders (in particular mobile app ones) for QR Code assume UTF-8 +encoding by default and do not support ECI. In this case supply UTF-8 data and +use the --binary switch: + +zint -b 58 --binary -d "UTF-8 data" 4.11 Batch processing --------------------- @@ -645,8 +665,9 @@ creates and then deletes a symbol: #include int main() { - struct zint_symbol *my_symbol;my_symbol = ZBarcode_Create(); - if(my_symbol != NULL) + struct zint_symbol *my_symbol; + my_symbol = ZBarcode_Create(); + if (my_symbol != NULL) { printf("Symbol successfully created!\n"); } @@ -721,8 +742,8 @@ The "rotate_angle" value can be used to rotate the image when outputting as a raster image. Valid values are 0, 90, 180 and 270. The ZBarcode_Encode_File() and ZBarcode_Encode_File_and_Print() functions can -be used to encode data read directly from a text file where the filename is given -in the "filename" string. +be used to encode data read directly from a text file where the filename is +given in the "filename" string. 5.4 Buffering Symbols in Memory ------------------------------- @@ -732,8 +753,8 @@ allow you to do this: int ZBarcode_Buffer(struct zint_symbol *symbol, int rotate_angle); -int ZBarcide_Encode_and_Buffer(struct zint_symbol *symbol, unsigned char - *input, int length, int rotate_angle); +int ZBarcide_Encode_and_Buffer(struct zint_symbol *symbol, unsigned char *input, + int length, int rotate_angle); int ZBarcode_Encode_File_and_Buffer(struct zint_symbol *symbol, char *filename, int rotate_angle); @@ -905,16 +926,16 @@ int main(int argc, char **argv) my_symbol = ZBarcode_Create(); strcpy(my_symbol->fgcolour, "nonsense"); error = ZBarcode_Encode_and_Print(my_symbol, argv[1], 0, 0); - if(error != 0) + if (error != 0) { - /* some error occurred */ + /* some warning or error occurred */ printf("%s\n", my_symbol->errtxt); } - if(error > WARN_INVALID_OPTION) + if (error >= ZINT_ERROR_TOO_LONG) { - /* stop now */ + /* stop now */ ZBarcode_Delete(my_symbol); - return 1; + return 1; } /* otherwise carry on with the rest of the application */ ZBarcode_Delete(my_symbol); @@ -1045,8 +1066,8 @@ Value | 5.8 Adjusting other output options ---------------------------------- The output_options variable can be used to adjust various aspects of the output -file. To select more than one option from the table below simply add them together -when adjusting this value: +file. To select more than one option from the table below simply add them +together when adjusting this value: my_symbol->output_options += BARCODE_BIND + READER_INIT; @@ -1104,7 +1125,7 @@ This function allows you to check whether a given symbology is available. A non-zero return value indicates that the given symbology is available. For example: -if(ZBarcode_ValidID(BARCODE_PDF417) != 0) { +if (ZBarcode_ValidID(BARCODE_PDF417) != 0) { printf("PDF417 available"); } else { printf("PDF417 not available"); @@ -1146,8 +1167,8 @@ numeric input (digits 0-9). 6.1.2.2 IATA Code 2 of 5 ------------------------ Used for baggage handling in the air-transport industry by the International -Air Transport Agency, this self-checking code will encode any length numeric input -(digits 0-9) and does not include a check digit. +Air Transport Agency, this self-checking code will encode any length numeric +input (digits 0-9) and does not include a check digit. 6.1.2.3 Industrial Code 2 of 5 ------------------------------ @@ -1258,8 +1279,8 @@ and validates the check digit before encoding. 6.1.4.2 SBN, ISBN and ISBN-13 ----------------------------- EAN-13 symbols (also known as Bookland EAN-13) can also be produced from -9-digit SBN, 10-digit ISBN or 13-digit ISBN-13 data. The relevant check digit needs -to be present in the input data and will be verified before the symbol is +9-digit SBN, 10-digit ISBN or 13-digit ISBN-13 data. The relevant check digit +needs to be present in the input data and will be verified before the symbol is generated. In addition EAN-2 and EAN-5 add-on symbols can be added using the + symbol as with UPC symbols. @@ -1340,7 +1361,8 @@ check digit. --------------- A variation of Code 39 used by the Italian Ministry of Health ("Ministero della Sanità") for encoding identifiers on pharmaceutical products. This symbology -requires a numeric input up to 8 digits in length. A check digit is added by Zint. +requires a numeric input up to 8 digits in length. A check digit is added by +Zint. 6.1.8.7 HIBC Code 39 -------------------- @@ -1425,7 +1447,8 @@ Also known as RSS (Reduced Spaced Symbology) these symbols are due to replace GS1-128 symbols in accordance with the GS1 General Specification. If a GS1 DataBar symbol is to be printed with a 2D component as specified in ISO 24723 set option_1 = 2 or use the option --mode=2 at the command prompt. See section -6.3 of this manual to find out how to generate DataBar symbols with 2D components. +6.3 of this manual to find out how to generate DataBar symbols with 2D +components. 6.1.12.1 DataBar-14 and DataBar-14 Truncated -------------------------------------------- @@ -1504,8 +1527,8 @@ error = ZBarcode_Encode(my_symbol, "That"); error = ZBarcode_Print(my_symbol); -A more sophisticated method is to use some type of line indexing which -indicates to the barcode reader which order the symbols should be read. This is +A more sophisticated method is to use some type of line indexing which indicates +to the barcode reader which order the symbols should be read. This is demonstrated by the symbologies below. 6.2.2 Codablock-F @@ -1580,8 +1603,8 @@ Input is the same as for GS1 DataBar Expanded (see section 6.1.12.3). In addition the width of the symbol can be altered using the --cols switch or option_2. In this case the number of columns relates to the number of character pairs on each row of the symbol. This symbol can be generated with a two- -dimensional component to make a composite symbol. For symbols with a 2D component -the number of columns must be at least 2. +dimensional component to make a composite symbol. For symbols with a 2D +component the number of columns must be at least 2. 6.2.10 Code 49 ------------- @@ -1743,11 +1766,11 @@ requires an 8-digit DPID input. 6.5.2 Dutch Post KIX Code ------------------------- -This Symbology is used by Royal Dutch TPG Post (Netherlands) for Postal code +This symbology is used by Royal Dutch TPG Post (Netherlands) for Postal code and automatic mail sorting. Data input can consist of numbers 0-9 and letters A-Z and needs to be 11 characters in length. No check digit is included. -6.5.3 Royal Mail 4-State Country Code (RM4SCC) +6.5.3 Royal Mail 4-State Customer Code (RM4SCC) ---------------------------------------------- The RM4SCC standard is used by the Royal Mail in the UK to encode postcode and customer data on mail items. Data input can consist of numbers 0-9 and letters @@ -1949,6 +1972,10 @@ conversion to Shift-JIS being carried out by Zint. A separate symbology ID can be used to encode Health Industry Barcode (HIBC) data which adds a leading '+' character and a modulo-49 check digit to the encoded data. +Non-ASCII data density may be maximized by using the --fullmultibyte switch or +by setting option_3 to ZINT_FULL_MULTIBYTE, but check that your barcode reader +supports this before using. + 6.6.3 Micro QR Code (ISO 18004) ------------------------------- A miniature version of the QR Code symbol for short messages. ECC levels can be @@ -1969,6 +1996,9 @@ Input | Version | Symbol Size 4 | M4 | 17 x 17 --------------------------------- +For barcode readers that support it, non-ASCII data density may be maximized by +using the --fullmultibyte switch or by setting option_3 to ZINT_FULL_MULTIBYTE. + 6.6.4 Rectangular Micro QR Code (rMQR) -------------------------------------- A rectangular version of QR Code. Like QR code rMQR supports encoding of @@ -2033,13 +2063,16 @@ Input | Version | Symbol Size 38 | Fixed height 17 --------------------------------- +For barcode readers that support it, non-ASCII data density may be maximized by +using the --fullmultibyte switch or by setting option_3 to ZINT_FULL_MULTIBYTE. + 6.6.5 UPNQR (Univerzalnega Plačilnega Naloga QR) ------------------------------------------------ A variation of QR Code used by Združenje Bank Slovenije (Bank Association of Slovenia). The size, error correction level and ECI are set by Zint and do not -need to be specified. UPNQR is unusual in that it uses ISO-8859-2 formatted data. -Zint will accept UTF-8 data and convert it to ISO-8859-2, or if your data is -already ISO-8859-2 formatted use the --binary switch or if using the API set +need to be specified. UPNQR is unusual in that it uses ISO-8859-2 formatted +data. Zint will accept UTF-8 data and convert it to ISO-8859-2, or if your data +is already ISO-8859-2 formatted use the --binary switch or if using the API set symbol->input_mode = DATA MODE; The following example creates a symbol from data saved as an ISO-8859-2 file: @@ -2068,8 +2101,8 @@ Characters | Meaning 13 - 15 | Three digit service code. This depends on your parcel courier. ---------------------------------------------------------------------------- -The primary message can be set at the command prompt using the --primary= switch. -The secondary message uses the normal data entry method. For example: +The primary message can be set at the command prompt using the --primary= +switch. The secondary message uses the normal data entry method. For example: zint -o test.eps -b 57 --primary='999999999840012' -d 'Secondary Message Here' @@ -2261,6 +2294,10 @@ Mode | Error Correction Capacity 5 | Approximately 50% ---------------------------------- +Non-ASCII data density may be maximized by using the --fullmultibyte switch or +by setting option_3 to ZINT_FULL_MULTIBYTE, but check that your barcode reader +supports this before using. + 6.6.11 DotCode ------------- DotCode uses a grid of dots in a rectangular formation to encode characters up @@ -2275,8 +2312,7 @@ error correction codewords. 6.6.12 Han Xin Code ------------------- -Also known as Chinese Sensible Code, Han Xin is a symbology which is still -under +Also known as Chinese Sensible Code, Han Xin is a symbology which is still under development, so it is recommended it should not yet be used for a production environment. The symbology is capable of encoding characters in the GB18030 character set (up to 4-byte characters) and is also able to support the ECI @@ -2387,6 +2423,10 @@ Mode | Recovery Capacity 4 | Approx 30% -------------------------- +Non-ASCII data density may be maximized by using the --fullmultibyte switch or +by setting option_3 to ZINT_FULL_MULTIBYTE, but check that your barcode reader +supports this before using. + 6.7 Other Barcode-Like Markings ------------------------------- 6.7.1. Facing Identification Mark (FIM) @@ -2424,7 +2464,7 @@ are ignored. ================================ 7.1 License ----------- -Zint, libzint and Zint Barcode Studio are Copyright © 2016 Robin Stuart. All +Zint, libzint and Zint Barcode Studio are Copyright © 2020 Robin Stuart. All historical versions are distributed under the GNU General Public License version 3 or later. Version 2.5 is released under a dual license: the encoding library is released under the BSD license whereas the GUI, Zint Barcode Studio, @@ -2654,8 +2694,8 @@ v2.6.3 - New symbology Royal Mail 4-state Mailmark. Added North America VIN verification. Bugfixes for TIF and EMF output and escape character handling. 15/02/2018 -v2.6.4 - Datamatrix DMRE updated to the ISO/IEC29158 version. This is incompatible -in the way, that the old -vers numbers for DMRE are re-assigned. +v2.6.4 - Datamatrix DMRE updated to the ISO/IEC29158 version. This is +incompatible in the way, that the old -vers numbers for DMRE are re-assigned. The separator of GS1-datamatrix may be switched from FNC1 to GS. GS1 field length check AI 8009 and 7230 to 7239 currected. @@ -2671,7 +2711,8 @@ v2.7.0 - new features: - New GS1 AIs 7240, 235, 417, 7040, 8026, updated checks for 7007, 8008 - New Symbology rMQR - QR and Gridmatrix optimisation for GB2312 -- removed depreciated interface for gLabels program. Please use current interface. +- removed depreciated interface for gLabels program. Please use current + interface. 7.4 Sources of Information -------------------------- @@ -2706,8 +2747,8 @@ international standards: > ISO/IEC 12323:2005 AIDC technologies - Symbology specifications - Code 16K > ISO/IEC 15417:2007 Information technology - Automatic identification and data capture techniques - Code 128 bar code symbology specification -> ISO/IEC 15438:20062015 Information technology - Automatic identification and - data capture techniques - PDF417 bar code symbology specification +> ISO/IEC 15438:2015 Information technology - Automatic identification and data + capture techniques - PDF417 bar code symbology specification > ISO/IEC 16022:2006 Information technology - Automatic identification and data capture techniques - Data Matrix ECC200 bar code symbology specification > ISO/IEC 16023:2000 Information technology - International symbology @@ -2716,6 +2757,9 @@ international standards: capture techniques - Code 39 bar code symbology specification > ISO/IEC 18004:2015 Information technology - Automatic identification and data capture techniques - QR Code bar code symbology specification +> ISO/IEC DIS 20830:2019 (Draft 2019-10-10) Information technology - Automatic + identification and data capture techniques - Han Xin Code bar code + symbology specification > ISO/IEC 24723:2010 Information technology - Automatic identification and data capture techniques - GS1 Composite bar code symbology specification > ISO/IEC 24724:2011 Information technology - Automatic identification and data @@ -2724,6 +2768,9 @@ international standards: capture techniques - MicroPDF417 bar code symbology specification > ISO/IEC 24778:2008 Information technology - Automatic identification and data capture techniques - Aztec Code bar code symbology specification +> ISO/IEC JTC1/SC31N000 (Draft 2018-6-8) Information technology - Automatic + identification and data capture techniques - Rectangular Micro QR Code + (rMQR) bar code symbology specification > Uniform Symbology Specification Code One (AIM Inc., 1994) > ANSI/AIM BC12-1998 - Uniform Symbology Specification Channel Code > ANSI/AIM BC6-2000 - Uniform Symbology Specification Code 49 @@ -2736,9 +2783,7 @@ international standards: > AIMD014 (v 1.63) - Information technology, Automatic identification and data capture techniques - Bar code symbology specification - Grid Matrix (Released 9th Dec 2008) -> AIMD-015:2010 (v 0.8) – DRAFT Bar code symbology specification – Han Xin Code - (Revised 25th March 2010) -> GS1 General Specifications Version 8.0 +> GS1 General Specifications Release 20.0 (Jan 2020) > AIM ITS/04-001 International Technical Standard – Extended Channel Interpretations Part 1: Identification Schemes and Protocol (Released 24th May 2004) diff --git a/frontend/main.c b/frontend/main.c index bbda6326..53746855 100644 --- a/frontend/main.c +++ b/frontend/main.c @@ -2,7 +2,7 @@ /* libzint - the open source barcode library - Copyright (C) 2008-2016 Robin Stuart + Copyright (C) 2008-2020 Robin Stuart 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 @@ -96,6 +96,7 @@ void usage(void) { " --esc Process escape characters in input data\n" " --filetype=TYPE Set output file type (PNG/EPS/SVG/PNG/EPS/GIF/TXT)\n" " --fg=COLOUR Specify a foreground colour (in hex)\n" + " --fullmultibyte Use multibyte mode for binary and Latin (QR Code/Han Xin/Grid Matrix)\n" " --gs1 Treat input as GS1 compatible data\n" " --gssep Use separator GS for GS1\n" " -h, --help Display help message\n" @@ -377,6 +378,20 @@ int batch_process(struct zint_symbol *symbol, char *filename, int mirror_mode, c return error_number; } +int is_fullmultibyte(struct zint_symbol* symbol) { + switch (symbol->symbology) { + case BARCODE_QRCODE: + case BARCODE_MICROQR: + //case BARCODE_HIBC_QR: Note character set restricted to ASCII subset + //case BARCODE_UPNQR: Note does not use Kanji mode + case BARCODE_RMQR: + case BARCODE_HANXIN: + case BARCODE_GRIDMATRIX: + return 1; + } + return 0; +} + int main(int argc, char **argv) { struct zint_symbol *my_symbol; int error_number; @@ -384,6 +399,7 @@ int main(int argc, char **argv) { int generated; int batch_mode; int mirror_mode; + int fullmultibyte; char filetype[4]; int i; @@ -394,6 +410,7 @@ int main(int argc, char **argv) { my_symbol->input_mode = UNICODE_MODE; batch_mode = 0; mirror_mode = 0; + fullmultibyte = 0; for (i = 0; i < 4; i++) { filetype[i] = '\0'; @@ -435,6 +452,7 @@ int main(int argc, char **argv) { {"gs1", 0, 0, 0}, {"gssep", 0, 0, 0}, {"binary", 0, 0, 0}, + {"fullmultibyte", 0, 0, 0}, {"notext", 0, 0, 0}, {"square", 0, 0, 0}, {"dmre", 0, 0, 0}, @@ -505,6 +523,9 @@ int main(int argc, char **argv) { if (!strcmp(long_options[option_index].name, "bg")) { strncpy(my_symbol->bgcolour, optarg, 7); } + if (!strcmp(long_options[option_index].name, "fullmultibyte")) { + fullmultibyte = 1; + } if (!strcmp(long_options[option_index].name, "notext")) { my_symbol->show_hrt = 0; } @@ -706,6 +727,9 @@ int main(int argc, char **argv) { strcat(my_symbol->outfile, "."); strcat(my_symbol->outfile, filetype); } + if (fullmultibyte && is_fullmultibyte(my_symbol)) { + my_symbol->option_3 = ZINT_FULL_MULTIBYTE; + } error_number = ZBarcode_Encode(my_symbol, (unsigned char*) optarg, strlen(optarg)); generated = 1; if (error_number != 0) { @@ -729,6 +753,9 @@ int main(int argc, char **argv) { break; case 'i': /* Take data from file */ + if (fullmultibyte && is_fullmultibyte(my_symbol)) { + my_symbol->option_3 = ZINT_FULL_MULTIBYTE; + } if (batch_mode == 0) { error_number = ZBarcode_Encode_File(my_symbol, optarg); generated = 1;