summaryrefslogtreecommitdiff
path: root/ext/mbstring/libmbfl/filters/mbfilter_sjis_mobile.c
diff options
context:
space:
mode:
Diffstat (limited to 'ext/mbstring/libmbfl/filters/mbfilter_sjis_mobile.c')
-rw-r--r--ext/mbstring/libmbfl/filters/mbfilter_sjis_mobile.c1034
1 files changed, 474 insertions, 560 deletions
diff --git a/ext/mbstring/libmbfl/filters/mbfilter_sjis_mobile.c b/ext/mbstring/libmbfl/filters/mbfilter_sjis_mobile.c
index 68084a0e0a..34acccbc2d 100644
--- a/ext/mbstring/libmbfl/filters/mbfilter_sjis_mobile.c
+++ b/ext/mbstring/libmbfl/filters/mbfilter_sjis_mobile.c
@@ -36,120 +36,103 @@
#include "emoji2uni.h"
extern int mbfl_bisec_srch2(int w, const unsigned short tbl[], int n);
-extern int mbfl_filt_ident_sjis(int c, mbfl_identify_filter *filter);
extern const unsigned char mblen_table_sjis[];
+static int mbfl_filt_conv_sjis_wchar_flush(mbfl_convert_filter *filter);
+
static const char *mbfl_encoding_sjis_docomo_aliases[] = {"SJIS-DOCOMO", "shift_jis-imode", "x-sjis-emoji-docomo", NULL};
static const char *mbfl_encoding_sjis_kddi_aliases[] = {"SJIS-KDDI", "shift_jis-kddi", "x-sjis-emoji-kddi", NULL};
static const char *mbfl_encoding_sjis_sb_aliases[] = {"SJIS-SOFTBANK", "shift_jis-softbank", "x-sjis-emoji-softbank", NULL};
const mbfl_encoding mbfl_encoding_sjis_docomo = {
- mbfl_no_encoding_sjis_docomo,
- "SJIS-Mobile#DOCOMO",
- "Shift_JIS",
- (const char *(*)[])&mbfl_encoding_sjis_docomo_aliases,
+ mbfl_no_encoding_sjis_docomo,
+ "SJIS-Mobile#DOCOMO",
+ "Shift_JIS",
+ mbfl_encoding_sjis_docomo_aliases,
mblen_table_sjis,
- MBFL_ENCTYPE_MBCS | MBFL_ENCTYPE_GL_UNSAFE,
+ MBFL_ENCTYPE_GL_UNSAFE,
&vtbl_sjis_docomo_wchar,
&vtbl_wchar_sjis_docomo
};
const mbfl_encoding mbfl_encoding_sjis_kddi = {
- mbfl_no_encoding_sjis_kddi,
- "SJIS-Mobile#KDDI",
- "Shift_JIS",
- (const char *(*)[])&mbfl_encoding_sjis_kddi_aliases,
+ mbfl_no_encoding_sjis_kddi,
+ "SJIS-Mobile#KDDI",
+ "Shift_JIS",
+ mbfl_encoding_sjis_kddi_aliases,
mblen_table_sjis,
- MBFL_ENCTYPE_MBCS | MBFL_ENCTYPE_GL_UNSAFE,
+ MBFL_ENCTYPE_GL_UNSAFE,
&vtbl_sjis_kddi_wchar,
&vtbl_wchar_sjis_kddi
};
const mbfl_encoding mbfl_encoding_sjis_sb = {
- mbfl_no_encoding_sjis_sb,
- "SJIS-Mobile#SOFTBANK",
- "Shift_JIS",
- (const char *(*)[])&mbfl_encoding_sjis_sb_aliases,
+ mbfl_no_encoding_sjis_sb,
+ "SJIS-Mobile#SOFTBANK",
+ "Shift_JIS",
+ mbfl_encoding_sjis_sb_aliases,
mblen_table_sjis,
- MBFL_ENCTYPE_MBCS | MBFL_ENCTYPE_GL_UNSAFE,
+ MBFL_ENCTYPE_GL_UNSAFE,
&vtbl_sjis_sb_wchar,
&vtbl_wchar_sjis_sb
};
-const struct mbfl_identify_vtbl vtbl_identify_sjis_docomo = {
- mbfl_no_encoding_sjis_docomo,
- mbfl_filt_ident_common_ctor,
- mbfl_filt_ident_sjis
-};
-
-const struct mbfl_identify_vtbl vtbl_identify_sjis_kddi = {
- mbfl_no_encoding_sjis_kddi,
- mbfl_filt_ident_common_ctor,
- mbfl_filt_ident_sjis
-};
-
-const struct mbfl_identify_vtbl vtbl_identify_sjis_sb = {
- mbfl_no_encoding_sjis_sb,
- mbfl_filt_ident_common_ctor,
- mbfl_filt_ident_sjis
-};
-
const struct mbfl_convert_vtbl vtbl_sjis_docomo_wchar = {
- mbfl_no_encoding_sjis_docomo,
- mbfl_no_encoding_wchar,
- mbfl_filt_conv_common_ctor,
+ mbfl_no_encoding_sjis_docomo,
+ mbfl_no_encoding_wchar,
+ mbfl_filt_conv_common_ctor,
+ NULL,
+ mbfl_filt_conv_sjis_mobile_wchar,
+ mbfl_filt_conv_sjis_wchar_flush,
NULL,
- mbfl_filt_conv_sjis_mobile_wchar,
- mbfl_filt_conv_common_flush,
- NULL,
};
const struct mbfl_convert_vtbl vtbl_wchar_sjis_docomo = {
- mbfl_no_encoding_wchar,
- mbfl_no_encoding_sjis_docomo,
- mbfl_filt_conv_common_ctor,
+ mbfl_no_encoding_wchar,
+ mbfl_no_encoding_sjis_docomo,
+ mbfl_filt_conv_common_ctor,
+ NULL,
+ mbfl_filt_conv_wchar_sjis_mobile,
+ mbfl_filt_conv_sjis_mobile_flush,
NULL,
- mbfl_filt_conv_wchar_sjis_mobile,
- mbfl_filt_conv_sjis_mobile_flush,
- NULL,
};
const struct mbfl_convert_vtbl vtbl_sjis_kddi_wchar = {
- mbfl_no_encoding_sjis_kddi,
- mbfl_no_encoding_wchar,
- mbfl_filt_conv_common_ctor,
+ mbfl_no_encoding_sjis_kddi,
+ mbfl_no_encoding_wchar,
+ mbfl_filt_conv_common_ctor,
+ NULL,
+ mbfl_filt_conv_sjis_mobile_wchar,
+ mbfl_filt_conv_sjis_wchar_flush,
NULL,
- mbfl_filt_conv_sjis_mobile_wchar,
- mbfl_filt_conv_common_flush,
- NULL,
};
const struct mbfl_convert_vtbl vtbl_wchar_sjis_kddi = {
- mbfl_no_encoding_wchar,
- mbfl_no_encoding_sjis_kddi,
- mbfl_filt_conv_common_ctor,
+ mbfl_no_encoding_wchar,
+ mbfl_no_encoding_sjis_kddi,
+ mbfl_filt_conv_common_ctor,
NULL,
- mbfl_filt_conv_wchar_sjis_mobile,
+ mbfl_filt_conv_wchar_sjis_mobile,
mbfl_filt_conv_sjis_mobile_flush,
NULL,
};
const struct mbfl_convert_vtbl vtbl_sjis_sb_wchar = {
- mbfl_no_encoding_sjis_sb,
- mbfl_no_encoding_wchar,
- mbfl_filt_conv_common_ctor,
+ mbfl_no_encoding_sjis_sb,
+ mbfl_no_encoding_wchar,
+ mbfl_filt_conv_common_ctor,
+ NULL,
+ mbfl_filt_conv_sjis_mobile_wchar,
+ mbfl_filt_conv_sjis_wchar_flush,
NULL,
- mbfl_filt_conv_sjis_mobile_wchar,
- mbfl_filt_conv_common_flush,
- NULL,
};
const struct mbfl_convert_vtbl vtbl_wchar_sjis_sb = {
- mbfl_no_encoding_wchar,
- mbfl_no_encoding_sjis_sb,
- mbfl_filt_conv_common_ctor,
+ mbfl_no_encoding_wchar,
+ mbfl_no_encoding_sjis_sb,
+ mbfl_filt_conv_common_ctor,
NULL,
- mbfl_filt_conv_wchar_sjis_mobile,
+ mbfl_filt_conv_wchar_sjis_mobile,
mbfl_filt_conv_sjis_mobile_flush,
NULL,
};
@@ -195,467 +178,431 @@ const unsigned short mbfl_kddi2uni_pua_b[8][3] = {
{0x27e7, 0x2863, 0xf080},
};
+/* Regional Indicator Unicode codepoints are from 0x1F1E6-0x1F1FF
+ * These correspond to the letters A-Z
+ * To display the flag emoji for a country, two unicode codepoints are combined,
+ * which correspond to the two-letter code for that country
+ * This macro converts uppercase ASCII values to Regional Indicator codepoints */
#define NFLAGS(c) (0x1F1A5+(int)(c))
#define CK(statement) do { if ((statement) < 0) return (-1); } while (0)
-#define SJIS_ENCODE(c1,c2,s1,s2) \
- do { \
- s1 = c1; \
- s1--; \
- s1 >>= 1; \
- if ((c1) < 0x5f) { \
- s1 += 0x71; \
- } else { \
- s1 += 0xb1; \
- } \
- s2 = c2; \
- if ((c1) & 1) { \
- if ((c2) < 0x60) { \
- s2--; \
- } \
- s2 += 0x20; \
- } else { \
- s2 += 0x7e; \
- } \
+#define SJIS_ENCODE(c1,c2,s1,s2) \
+ do { \
+ s1 = ((c1 - 1) >> 1) + ((c1) < 0x5F ? 0x71 : 0xB1); \
+ s2 = c2; \
+ if ((c1) & 1) { \
+ if ((c2) < 0x60) { \
+ s2--; \
+ } \
+ s2 += 0x20; \
+ } else { \
+ s2 += 0x7e; \
+ } \
} while (0)
-#define SJIS_DECODE(c1,c2,s1,s2) \
- do { \
- s1 = c1; \
- if (s1 < 0xa0) { \
- s1 -= 0x81; \
- } else { \
- s1 -= 0xc1; \
- } \
- s1 <<= 1; \
- s1 += 0x21; \
- s2 = c2; \
- if (s2 < 0x9f) { \
- if (s2 < 0x7f) { \
- s2++; \
- } \
- s2 -= 0x20; \
- } else { \
- s1++; \
- s2 -= 0x7e; \
- } \
+#define SJIS_DECODE(c1,c2,s1,s2) \
+ do { \
+ if (c1 < 0xa0) { \
+ s1 = ((c1 - 0x81) << 1) + 0x21; \
+ } else { \
+ s1 = ((c1 - 0xc1) << 1) + 0x21; \
+ } \
+ s2 = c2; \
+ if (c2 < 0x9f) { \
+ if (c2 < 0x7f) { \
+ s2++; \
+ } \
+ s2 -= 0x20; \
+ } else { \
+ s1++; \
+ s2 -= 0x7e; \
+ } \
} while (0)
-#define CODE2JIS(c1,c2,s1,s2) \
- c1 = (s1)/94+0x21; \
- c2 = (s1)-94*((c1)-0x21)+0x21; \
- s1 = ((c1) << 8) | (c2); \
+/* (ku*94)+ten value -> Shift-JIS byte sequence */
+#define CODE2JIS(c1,c2,s1,s2) \
+ c1 = (s1)/94+0x21; \
+ c2 = (s1)-94*((c1)-0x21)+0x21; \
+ s1 = ((c1) << 8) | (c2); \
s2 = 1
-int
-mbfilter_conv_map_tbl(int c, int *w, const unsigned short map[][3], int n)
+int mbfilter_conv_map_tbl(int c, int *w, const unsigned short map[][3], int n)
{
- int i, match = 0;
-
- for (i = 0; i < n; i++) {
+ for (int i = 0; i < n; i++) {
if (map[i][0] <= c && c <= map[i][1]) {
*w = c - map[i][0] + map[i][2];
- match = 1;
- break;
+ return 1;
}
}
- return match;
+ return 0;
}
-int
-mbfilter_conv_r_map_tbl(int c, int *w, const unsigned short map[][3], int n)
+int mbfilter_conv_r_map_tbl(int c, int *w, const unsigned short map[][3], int n)
{
- int i, match = 0;
-
- for (i = 0; i < n; i++) {
+ /* Convert in reverse direction */
+ for (int i = 0; i < n; i++) {
if (map[i][2] <= c && c <= map[i][2] - map[i][0] + map[i][1]) {
*w = c + map[i][0] - map[i][2];
- match = 1;
- break;
+ return 1;
}
}
- return match;
+ return 0;
}
-int
-mbfilter_sjis_emoji_docomo2unicode(int s, int *snd)
+/* number -> (ku*94)+ten value for telephone keypad character */
+#define DOCOMO_KEYPAD(n) ((n) == 0 ? 0x296F : (0x2965 + (n)))
+#define DOCOMO_KEYPAD_HASH 0x2964
+
+#define EMIT_KEYPAD_EMOJI(c) do { *snd = (c); return 0x20E3; } while(0)
+
+/* Unicode codepoints for emoji are above 0x1F000, but we only store 16-bits
+ * in our tables. Therefore, add 0x10000 to recover the true values.
+ *
+ * Again, for some emoji which are not supported by Unicode, we use codepoints
+ * in the Private Use Area above 0xFE000. Again, add 0xF0000 to recover the
+ * true value. */
+static inline int convert_emoji_cp(int cp)
{
- int w = s;
+ if (cp > 0xF000)
+ return cp + 0x10000;
+ else if (cp > 0xE000)
+ return cp + 0xF0000;
+ return cp;
+}
+
+int mbfilter_sjis_emoji_docomo2unicode(int s, int *snd)
+{
+ /* All three mobile vendors had emoji for numbers on a telephone keypad
+ * Unicode doesn't have those, but it has a combining character which puts
+ * a 'keypad button' around the following character, making it look like
+ * a key on a telephone or keyboard. That combining char is codepoint 0x20E3. */
if (s >= mb_tbl_code2uni_docomo1_min && s <= mb_tbl_code2uni_docomo1_max) {
- if (s >= mb_tbl_code2uni_docomo1_min + 0x00a2 &&
- s <= mb_tbl_code2uni_docomo1_min + 0x00ad &&
- s != mb_tbl_code2uni_docomo1_min + 0x00a3) {
- w = 0x20E3;
- *snd = mb_tbl_code2uni_docomo1[s - mb_tbl_code2uni_docomo1_min];
- if (*snd > 0xf000) {
- *snd += 0x10000;
- }
+ if ((s >= DOCOMO_KEYPAD(1) && s <= DOCOMO_KEYPAD(9)) || s == DOCOMO_KEYPAD(0) || s == DOCOMO_KEYPAD_HASH) {
+ EMIT_KEYPAD_EMOJI(convert_emoji_cp(mb_tbl_code2uni_docomo1[s - mb_tbl_code2uni_docomo1_min]));
} else {
- w = mb_tbl_code2uni_docomo1[s - mb_tbl_code2uni_docomo1_min];
- if (w > 0xf000) {
- w += 0x10000;
- } else if (w > 0xe000) { /* unsupported by Unicode 6.0 */
- w += 0xf0000;
- }
*snd = 0;
- if (!w) {
- w = s;
- }
+ return convert_emoji_cp(mb_tbl_code2uni_docomo1[s - mb_tbl_code2uni_docomo1_min]);
}
}
-
- return w;
+ return 0;
}
-int
-mbfilter_sjis_emoji_kddi2unicode(int s, int *snd)
-{
- int w = s, si, c;
- const int nflags_order_kddi[] = {3, 1, 5, 4, 0, 7};
+#define EMIT_FLAG_EMOJI(country) do { *snd = NFLAGS((country)[0]); return NFLAGS((country)[1]); } while(0)
+
+static const char nflags_kddi[6][2] = {"FR", "DE", "IT", "GB", "CN", "KR"};
- *snd = 0;
+int mbfilter_sjis_emoji_kddi2unicode(int s, int *snd)
+{
if (s >= mb_tbl_code2uni_kddi1_min && s <= mb_tbl_code2uni_kddi1_max) {
- si = s - mb_tbl_code2uni_kddi1_min;
- if (si == 0x0008) { /* ES */
- *snd = NFLAGS(nflags_s[2][0]); w = NFLAGS(nflags_s[2][1]);
- } else if (si == 0x0009) { /* RU */
- *snd = NFLAGS(nflags_s[8][0]); w = NFLAGS(nflags_s[8][1]);
- } else if (si >= 0x008d && si <= 0x0092) {
- c = nflags_order_kddi[si-0x008d];
- *snd = NFLAGS(nflags_s[c][0]); w = NFLAGS(nflags_s[c][1]);
- } else if (si == 0x0104) {
- *snd = 0x0023; w = 0x20E3;
+ if (s == 0x24C0) { /* Spain */
+ EMIT_FLAG_EMOJI("ES");
+ } else if (s == 0x24C1) { /* Russia */
+ EMIT_FLAG_EMOJI("RU");
+ } else if (s >= 0x2545 && s <= 0x254A) {
+ EMIT_FLAG_EMOJI(nflags_kddi[s - 0x2545]);
+ } else if (s == 0x25BC) {
+ EMIT_KEYPAD_EMOJI('#');
} else {
- w = mb_tbl_code2uni_kddi1[si];
- if (w > 0xf000) {
- w += 0x10000;
- } else if (w > 0xe000) { /* unsupported by Unicode 6.0 */
- w += 0xf0000;
- }
+ *snd = 0;
+ return convert_emoji_cp(mb_tbl_code2uni_kddi1[s - mb_tbl_code2uni_kddi1_min]);
}
} else if (s >= mb_tbl_code2uni_kddi2_min && s <= mb_tbl_code2uni_kddi2_max) {
- si = s - mb_tbl_code2uni_kddi2_min;
- if (si == 100) { /* JP */
- *snd = NFLAGS(nflags_s[6][0]); w = NFLAGS(nflags_s[6][1]);
- } else if (si >= 0x00ba && si <= 0x00c2) {
- *snd = si-0x00ba+0x0031; w = 0x20E3;
- } else if (si == 0x010b) { /* US */
- *snd = NFLAGS(nflags_s[9][0]); w = NFLAGS(nflags_s[9][1]);
- } else if (si == 0x0144) {
- *snd = 0x0030; w = 0x20E3;
+ if (s == 0x2750) { /* Japan */
+ EMIT_FLAG_EMOJI("JP");
+ } else if (s >= 0x27A6 && s <= 0x27AE) {
+ EMIT_KEYPAD_EMOJI(s - 0x27A6 + '1');
+ } else if (s == 0x27F7) { /* United States */
+ EMIT_FLAG_EMOJI("US");
+ } else if (s == 0x2830) {
+ EMIT_KEYPAD_EMOJI('0');
} else {
- w = mb_tbl_code2uni_kddi2[si];
- if (w > 0xf000) {
- w += 0x10000;
- } else if (w > 0xe000) { /* unsupported by Unicode 6.0 */
- w += 0xf0000;
- }
+ *snd = 0;
+ return convert_emoji_cp(mb_tbl_code2uni_kddi2[s - mb_tbl_code2uni_kddi2_min]);
}
}
- return w;
+ return 0;
}
-int
-mbfilter_sjis_emoji_sb2unicode(int s, int *snd)
+static const char nflags_sb[10][2] = {"JP", "US", "FR", "DE", "IT", "GB", "ES", "RU", "CN", "KR"};
+
+int mbfilter_sjis_emoji_sb2unicode(int s, int *snd)
{
- int w = s, si, c;
- const int nflags_order_sb[10] = {6, 9, 3, 1, 5, 4, 2, 8, 0, 7};
-
- *snd = 0;
- if (s >= mb_tbl_code2uni_sb1_min && s <= mb_tbl_code2uni_sb1_max) {
- si = s - mb_tbl_code2uni_sb1_min;
- if (si == 0x006e || (si >= 0x007a && si <= 0x0083)) {
- *snd = mb_tbl_code2uni_sb1[si];
- if (*snd > 0xf000) {
- *snd += 0x10000;
- }
- w = 0x20E3;
+ if (s >= mb_tbl_code2uni_sb1_min && s <= mb_tbl_code2uni_sb1_max) {
+ if (s == 0x2817 || (s >= 0x2823 && s <= 0x282C)) {
+ EMIT_KEYPAD_EMOJI(mb_tbl_code2uni_sb1[s - mb_tbl_code2uni_sb1_min]);
} else {
- w = mb_tbl_code2uni_sb1[si];
- if (w > 0xf000) {
- w += 0x10000;
- } else if (w > 0xe000) { /* unsupported by Unicode 6.0 */
- w += 0xf0000;
- }
+ *snd = 0;
+ return convert_emoji_cp(mb_tbl_code2uni_sb1[s - mb_tbl_code2uni_sb1_min]);
}
} else if (s >= mb_tbl_code2uni_sb2_min && s <= mb_tbl_code2uni_sb2_max) {
- si = s - mb_tbl_code2uni_sb2_min;
- w = mb_tbl_code2uni_sb2[si];
- if (w > 0xf000) {
- w += 0x10000;
- } else if (w > 0xe000) { /* unsupported by Unicode 6.0 */
- w += 0xf0000;
- }
+ *snd = 0;
+ return convert_emoji_cp(mb_tbl_code2uni_sb2[s - mb_tbl_code2uni_sb2_min]);
} else if (s >= mb_tbl_code2uni_sb3_min && s <= mb_tbl_code2uni_sb3_max) {
- si = s - mb_tbl_code2uni_sb3_min;
- if (si >= 0x0069 && si <= 0x0072) {
- c = nflags_order_sb[si-0x0069];
- *snd = NFLAGS(nflags_s[c][0]); w = NFLAGS(nflags_s[c][1]);
+ if (s >= 0x2B02 && s <= 0x2B0B) {
+ EMIT_FLAG_EMOJI(nflags_sb[s - 0x2B02]);
} else {
- w = mb_tbl_code2uni_sb3[si];
- if (w > 0xf000) {
- w += 0x10000;
- } else if (w > 0xe000) { /* unsupported by Unicode 6.0 */
- w += 0xf0000;
- }
+ *snd = 0;
+ return convert_emoji_cp(mb_tbl_code2uni_sb3[s - mb_tbl_code2uni_sb3_min]);
}
}
- return w;
+ return 0;
}
int
mbfilter_unicode2sjis_emoji_docomo(int c, int *s1, mbfl_convert_filter *filter)
{
- int i, match = 0, c1s;
-
+ /* When converting SJIS-Mobile to Unicode, we convert keypad symbol emoji
+ * to a sequence of 2 codepoints, one of which is a combining character which
+ * adds the 'key' image around the other
+ *
+ * In the other direction, look for such sequences and convert them to a
+ * single emoji */
if (filter->status == 1) {
- c1s = filter->cache;
- filter->cache = 0;
- filter->status = 0;
+ int c1 = filter->cache;
+ filter->cache = filter->status = 0;
if (c == 0x20E3) {
- if (c1s == 0x0023) {
+ if (c1 == '#') {
*s1 = 0x2964;
- match = 1;
- } else if (c1s == 0x0030) {
- *s1 = 0x296f;
- match = 1;
- } else if (c1s >= 0x0031 && c1s <= 0x0039) {
- *s1 = 0x2966 + (c1s - 0x0031);
- match = 1;
+ } else if (c1 == '0') {
+ *s1 = 0x296F;
+ } else { /* Previous character was '1'-'9' */
+ *s1 = 0x2966 + (c1 - '1');
}
+ return 1;
} else {
- CK((*filter->output_function)(c1s, filter->data));
- }
- } else {
- if (c == 0x0023 || (c >= 0x0030 && c<=0x0039)) {
- filter->status = 1;
- filter->cache = c;
- *s1 = -1;
- return match;
- }
-
- if (c == 0x00A9) {
- *s1 = 0x29b5; match = 1;
- } else if (c == 0x00AE) {
- *s1 = 0x29ba; match = 1;
- } else if (c >= mb_tbl_uni_docomo2code2_min && c <= mb_tbl_uni_docomo2code2_max) {
- i = mbfl_bisec_srch2(c, mb_tbl_uni_docomo2code2_key, mb_tbl_uni_docomo2code2_len);
- if (i >= 0) {
- *s1 = mb_tbl_uni_docomo2code2_value[i];
- match = 1;
- }
- } else if (c >= mb_tbl_uni_docomo2code3_min && c <= mb_tbl_uni_docomo2code3_max) {
- i = mbfl_bisec_srch2(c - 0x10000, mb_tbl_uni_docomo2code3_key, mb_tbl_uni_docomo2code3_len);
- if (i >= 0) {
- *s1 = mb_tbl_uni_docomo2code3_value[i];
- match = 1;
- }
- } else if (c >= mb_tbl_uni_docomo2code5_min && c <= mb_tbl_uni_docomo2code5_max) {
- i = mbfl_bisec_srch2(c - 0xf0000, mb_tbl_uni_docomo2code5_key, mb_tbl_uni_docomo2code5_len);
- if (i >= 0) {
- *s1 = mb_tbl_uni_docomo2code5_val[i];
- match = 1;
- }
+ /* This character wasn't combining character to make keypad symbol,
+ * so pass the previous character through... and proceed to process the
+ * current character as usual
+ * (Single-byte ASCII characters are valid in Shift-JIS...) */
+ CK((*filter->output_function)(c1, filter->data));
}
}
- return match;
+ if (c == '#' || (c >= '0' && c <= '9')) {
+ filter->status = 1;
+ filter->cache = c;
+ return 0;
+ }
+
+ if (c == 0xA9) { /* Copyright sign */
+ *s1 = 0x29B5;
+ return 1;
+ } else if (c == 0x00AE) { /* Registered sign */
+ *s1 = 0x29BA;
+ return 1;
+ } else if (c >= mb_tbl_uni_docomo2code2_min && c <= mb_tbl_uni_docomo2code2_max) {
+ int i = mbfl_bisec_srch2(c, mb_tbl_uni_docomo2code2_key, mb_tbl_uni_docomo2code2_len);
+ if (i >= 0) {
+ *s1 = mb_tbl_uni_docomo2code2_value[i];
+ return 1;
+ }
+ } else if (c >= mb_tbl_uni_docomo2code3_min && c <= mb_tbl_uni_docomo2code3_max) {
+ int i = mbfl_bisec_srch2(c - 0x10000, mb_tbl_uni_docomo2code3_key, mb_tbl_uni_docomo2code3_len);
+ if (i >= 0) {
+ *s1 = mb_tbl_uni_docomo2code3_value[i];
+ return 1;
+ }
+ } else if (c >= mb_tbl_uni_docomo2code5_min && c <= mb_tbl_uni_docomo2code5_max) {
+ int i = mbfl_bisec_srch2(c - 0xF0000, mb_tbl_uni_docomo2code5_key, mb_tbl_uni_docomo2code5_len);
+ if (i >= 0) {
+ *s1 = mb_tbl_uni_docomo2code5_val[i];
+ return 1;
+ }
+ }
+ return 0;
}
-int
-mbfilter_unicode2sjis_emoji_kddi(int c, int *s1, mbfl_convert_filter *filter)
+int mbfilter_unicode2sjis_emoji_kddi(int c, int *s1, mbfl_convert_filter *filter)
{
- int i, match = 0, c1s;
-
if (filter->status == 1) {
- c1s = filter->cache;
- filter->cache = 0;
- filter->status = 0;
+ int c1 = filter->cache;
+ filter->cache = filter->status = 0;
if (c == 0x20E3) {
- if (c1s == 0x0023) {
- *s1 = 0x25bc;
- match = 1;
- } else if (c1s == 0x0030) {
+ if (c1 == '#') {
+ *s1 = 0x25BC;
+ } else if (c1 == '0') {
*s1 = 0x2830;
- match = 1;
- } else if (c1s >= 0x0031 && c1s <= 0x0039) {
- *s1 = 0x27a6 + (c1s - 0x0031);
- match = 1;
- }
- } else if ((c >= NFLAGS(0x41) && c <= NFLAGS(0x5A)) && (c1s >= NFLAGS(0x41) && c1s <= NFLAGS(0x5A))) {
- for (i=0; i<10; i++) {
- if (c1s == NFLAGS(nflags_s[i][0]) && c == NFLAGS(nflags_s[i][1])) {
- *s1 = nflags_code_kddi[i];
- match = 1;
- break;
- }
+ } else { /* Previous character was '1'-'9' */
+ *s1 = 0x27a6 + (c1 - '1');
}
+ return 1;
} else {
- if (c1s >= ucs_a1_jis_table_min && c1s < ucs_a1_jis_table_max) {
- c1s = ucs_a1_jis_table[c1s - ucs_a1_jis_table_min];
- CK((*filter->output_function)(c1s, filter->data));
- }
+ CK((*filter->output_function)(c1, filter->data));
}
- } else {
- if (c == 0x0023 || ( c >= 0x0030 && c<=0x0039) ||
- (c >= NFLAGS(0x41) && c<= NFLAGS(0x5A))) {
- filter->status = 1;
- filter->cache = c;
- *s1 = -1;
- return match;
- }
-
- if (c == 0x00A9) {
- *s1 = 0x27dc; match = 1;
- } else if (c == 0x00AE) {
- *s1 = 0x27dd; match = 1;
- } else if (c >= mb_tbl_uni_kddi2code2_min && c <= mb_tbl_uni_kddi2code2_max) {
- i = mbfl_bisec_srch2(c, mb_tbl_uni_kddi2code2_key, mb_tbl_uni_kddi2code2_len);
- if (i >= 0) {
- *s1 = mb_tbl_uni_kddi2code2_value[i];
- match = 1;
- }
- } else if (c >= mb_tbl_uni_kddi2code3_min && c <= mb_tbl_uni_kddi2code3_max) {
- i = mbfl_bisec_srch2(c - 0x10000, mb_tbl_uni_kddi2code3_key, mb_tbl_uni_kddi2code3_len);
- if (i >= 0) {
- *s1 = mb_tbl_uni_kddi2code3_value[i];
- match = 1;
- }
- } else if (c >= mb_tbl_uni_kddi2code5_min && c <= mb_tbl_uni_kddi2code5_max) {
- i = mbfl_bisec_srch2(c - 0xf0000, mb_tbl_uni_kddi2code5_key, mb_tbl_uni_kddi2code5_len);
- if (i >= 0) {
- *s1 = mb_tbl_uni_kddi2code5_val[i];
- match = 1;
+ } else if (filter->status == 2) {
+ int c1 = filter->cache;
+ filter->cache = filter->status = 0;
+ if (c >= NFLAGS('B') && c <= NFLAGS('U')) { /* B for GB, U for RU */
+ for (int i = 0; i < 10; i++) {
+ if (c1 == NFLAGS(nflags_s[i][0]) && c == NFLAGS(nflags_s[i][1])) {
+ *s1 = nflags_code_kddi[i];
+ return 1;
+ }
}
}
+
+ /* If none of the KDDI national flag emoji matched, then we have no way
+ * to convert the previous codepoint... */
+ mbfl_filt_conv_illegal_output(c1, filter);
+ }
+
+ if (c == '#' || (c >= '0' && c <= '9')) {
+ filter->status = 1;
+ filter->cache = c;
+ return 0;
+ } else if (c >= NFLAGS('C') && c <= NFLAGS('U')) { /* C for CN, U for US */
+ filter->status = 2;
+ filter->cache = c;
+ return 0;
}
- return match;
+ if (c == 0xA9) { /* Copyright sign */
+ *s1 = 0x27DC;
+ return 1;
+ } else if (c == 0xAE) { /* Registered sign */
+ *s1 = 0x27DD;
+ return 1;
+ } else if (c >= mb_tbl_uni_kddi2code2_min && c <= mb_tbl_uni_kddi2code2_max) {
+ int i = mbfl_bisec_srch2(c, mb_tbl_uni_kddi2code2_key, mb_tbl_uni_kddi2code2_len);
+ if (i >= 0) {
+ *s1 = mb_tbl_uni_kddi2code2_value[i];
+ return 1;
+ }
+ } else if (c >= mb_tbl_uni_kddi2code3_min && c <= mb_tbl_uni_kddi2code3_max) {
+ int i = mbfl_bisec_srch2(c - 0x10000, mb_tbl_uni_kddi2code3_key, mb_tbl_uni_kddi2code3_len);
+ if (i >= 0) {
+ *s1 = mb_tbl_uni_kddi2code3_value[i];
+ return 1;
+ }
+ } else if (c >= mb_tbl_uni_kddi2code5_min && c <= mb_tbl_uni_kddi2code5_max) {
+ int i = mbfl_bisec_srch2(c - 0xF0000, mb_tbl_uni_kddi2code5_key, mb_tbl_uni_kddi2code5_len);
+ if (i >= 0) {
+ *s1 = mb_tbl_uni_kddi2code5_val[i];
+ return 1;
+ }
+ }
+ return 0;
}
-int
-mbfilter_unicode2sjis_emoji_sb(int c, int *s1, mbfl_convert_filter *filter)
+int mbfilter_unicode2sjis_emoji_sb(int c, int *s1, mbfl_convert_filter *filter)
{
- int i, match = 0, c1s;
-
if (filter->status == 1) {
- filter->status = 0;
- c1s = filter->cache;
- filter->cache = 0;
+ int c1 = filter->cache;
+ filter->cache = filter->status = 0;
if (c == 0x20E3) {
- if (c1s == 0x0023) {
+ if (c1 == '#') {
*s1 = 0x2817;
- match = 1;
- } else if (c1s == 0x0030) {
+ } else if (c1 == '0') {
*s1 = 0x282c;
- match = 1;
- } else if (c1s >= 0x0031 && c1s <= 0x0039) {
- *s1 = 0x2823 + (c1s - 0x0031);
- match = 1;
+ } else { /* Previous character was '1'-'9' */
+ *s1 = 0x2823 + (c1 - '1');
}
- } else if ((c >= NFLAGS(0x41) && c <= NFLAGS(0x5A)) && (c1s >= NFLAGS(0x41) && c1s <= NFLAGS(0x5A))) {
- for (i=0; i<10; i++) {
- if (c1s == NFLAGS(nflags_s[i][0]) && c == NFLAGS(nflags_s[i][1])) {
+ return 1;
+ } else {
+ (*filter->output_function)(c1, filter->data);
+ }
+ } else if (filter->status == 2) {
+ int c1 = filter->cache;
+ filter->cache = filter->status = 0;
+ if (c >= NFLAGS('B') && c <= NFLAGS('U')) { /* B for GB, U for RU */
+ for (int i = 0; i < 10; i++) {
+ if (c1 == NFLAGS(nflags_s[i][0]) && c == NFLAGS(nflags_s[i][1])) {
*s1 = nflags_code_sb[i];
- match = 1;
- break;
+ return 1;
}
}
- } else {
- if (c1s >= ucs_a1_jis_table_min && c1s < ucs_a1_jis_table_max) {
- c1s = ucs_a1_jis_table[c1s - ucs_a1_jis_table_min];
- CK((*filter->output_function)(c1s, filter->data));
- }
}
- } else {
- if (c == 0x0023 || ( c >= 0x0030 && c<=0x0039) || (c >= NFLAGS(0x41) && c<= NFLAGS(0x5A))) {
- filter->status = 1;
- filter->cache = c;
- *s1 = -1;
- return match;
- }
-
- if (c == 0x00A9) {
- *s1 = 0x2855; match = 1;
- } else if (c == 0x00AE) {
- *s1 = 0x2856; match = 1;
- } else if (c >= mb_tbl_uni_sb2code2_min && c <= mb_tbl_uni_sb2code2_max) {
- i = mbfl_bisec_srch2(c, mb_tbl_uni_sb2code2_key, mb_tbl_uni_sb2code2_len);
- if (i >= 0) {
- *s1 = mb_tbl_uni_sb2code2_value[i];
- match = 1;
- }
- } else if (c >= mb_tbl_uni_sb2code3_min && c <= mb_tbl_uni_sb2code3_max) {
- i = mbfl_bisec_srch2(c - 0x10000, mb_tbl_uni_sb2code3_key, mb_tbl_uni_sb2code3_len);
- if (i >= 0) {
- *s1 = mb_tbl_uni_sb2code3_value[i];
- match = 1;
- }
- } else if (c >= mb_tbl_uni_sb2code5_min && c <= mb_tbl_uni_sb2code5_max) {
- i = mbfl_bisec_srch2(c - 0xf0000, mb_tbl_uni_sb2code5_key, mb_tbl_uni_sb2code5_len);
- if (i >= 0) {
- *s1 = mb_tbl_uni_sb2code5_val[i];
- match = 1;
- }
+
+ /* If none of the SoftBank national flag emoji matched, then we have no way
+ * to convert the previous codepoint... */
+ mbfl_filt_conv_illegal_output(c1, filter);
+ }
+
+ if (c == '#' || (c >= '0' && c <= '9')) {
+ filter->status = 1;
+ filter->cache = c;
+ return 0;
+ } else if (c >= NFLAGS('C') && c <= NFLAGS('U')) { /* C for CN, U for US */
+ filter->status = 2;
+ filter->cache = c;
+ return 0;
+ }
+
+ if (c == 0xA9) { /* Copyright sign */
+ *s1 = 0x2855;
+ return 1;
+ } else if (c == 0xAE) { /* Registered sign */
+ *s1 = 0x2856;
+ return 1;
+ } else if (c >= mb_tbl_uni_sb2code2_min && c <= mb_tbl_uni_sb2code2_max) {
+ int i = mbfl_bisec_srch2(c, mb_tbl_uni_sb2code2_key, mb_tbl_uni_sb2code2_len);
+ if (i >= 0) {
+ *s1 = mb_tbl_uni_sb2code2_value[i];
+ return 1;
+ }
+ } else if (c >= mb_tbl_uni_sb2code3_min && c <= mb_tbl_uni_sb2code3_max) {
+ int i = mbfl_bisec_srch2(c - 0x10000, mb_tbl_uni_sb2code3_key, mb_tbl_uni_sb2code3_len);
+ if (i >= 0) {
+ *s1 = mb_tbl_uni_sb2code3_value[i];
+ return 1;
+ }
+ } else if (c >= mb_tbl_uni_sb2code5_min && c <= mb_tbl_uni_sb2code5_max) {
+ int i = mbfl_bisec_srch2(c - 0xF0000, mb_tbl_uni_sb2code5_key, mb_tbl_uni_sb2code5_len);
+ if (i >= 0) {
+ *s1 = mb_tbl_uni_sb2code5_val[i];
+ return 1;
}
}
- return match;
+ return 0;
}
-/*
- * SJIS-win => wchar
- */
-int
-mbfl_filt_conv_sjis_mobile_wchar(int c, mbfl_convert_filter *filter)
+int mbfl_filt_conv_sjis_mobile_wchar(int c, mbfl_convert_filter *filter)
{
- int c1, s, s1 = 0, s2 = 0, w;
- int snd = 0;
+ int c1, s, s1, s2, w, snd = 0;
-retry:
switch (filter->status) {
case 0:
- if (c >= 0 && c < 0x80) { /* latin */
- if (filter->from->no_encoding == mbfl_no_encoding_sjis_sb && c == 0x1b) {
+ if (c >= 0 && c < 0x80) { /* ASCII */
+ if (filter->from == &mbfl_encoding_sjis_sb && c == 0x1B) {
+ /* ESC; escape sequences were used on older SoftBank phones for emoji */
filter->cache = c;
filter->status = 2;
} else {
CK((*filter->output_function)(c, filter->data));
}
- } else if (c > 0xa0 && c < 0xe0) { /* kana */
- CK((*filter->output_function)(0xfec0 + c, filter->data));
- } else if (c > 0x80 && c < 0xfd && c != 0xa0) { /* kanji first char */
+ } else if (c > 0xA0 && c < 0xE0) { /* Kana */
+ CK((*filter->output_function)(0xFEC0 + c, filter->data));
+ } else if (c > 0x80 && c < 0xFD && c != 0xA0) { /* Kanji, first byte */
filter->status = 1;
filter->cache = c;
} else {
- w = c & MBFL_WCSGROUP_MASK;
- w |= MBFL_WCSGROUP_THROUGH;
- CK((*filter->output_function)(w, filter->data));
+ CK((*filter->output_function)(c | MBFL_WCSGROUP_THROUGH, filter->data));
}
break;
- case 1: /* kanji second char */
+ case 1: /* Kanji, second byte */
filter->status = 0;
c1 = filter->cache;
- if (c >= 0x40 && c <= 0xfc && c != 0x7f) {
+ if (c >= 0x40 && c <= 0xFC && c != 0x7F) {
w = 0;
SJIS_DECODE(c1, c, s1, s2);
- s = (s1 - 0x21)*94 + s2 - 0x21;
+ s = ((s1 - 0x21) * 94) + s2 - 0x21;
if (s <= 137) {
if (s == 31) {
- w = 0xff3c; /* FULLWIDTH REVERSE SOLIDUS */
+ w = 0xFF3C; /* FULLWIDTH REVERSE SOLIDUS */
} else if (s == 32) {
- w = 0xff5e; /* FULLWIDTH TILDE */
+ w = 0xFF5E; /* FULLWIDTH TILDE */
} else if (s == 33) {
- w = 0x2225; /* PARALLEL TO */
+ w = 0x2225; /* PARALLEL TO */
} else if (s == 60) {
- w = 0xff0d; /* FULLWIDTH HYPHEN-MINUS */
+ w = 0xFF0D; /* FULLWIDTH HYPHEN-MINUS */
} else if (s == 80) {
- w = 0xffe0; /* FULLWIDTH CENT SIGN */
+ w = 0xFFE0; /* FULLWIDTH CENT SIGN */
} else if (s == 81) {
- w = 0xffe1; /* FULLWIDTH POUND SIGN */
+ w = 0xFFE1; /* FULLWIDTH POUND SIGN */
} else if (s == 137) {
- w = 0xffe2; /* FULLWIDTH NOT SIGN */
+ w = 0xFFE2; /* FULLWIDTH NOT SIGN */
}
}
if (w == 0) {
@@ -665,134 +612,123 @@ retry:
w = jisx0208_ucs_table[s];
} else if (s >= cp932ext2_ucs_table_min && s < cp932ext2_ucs_table_max) { /* vendor ext2 (89ku - 92ku) */
w = cp932ext2_ucs_table[s - cp932ext2_ucs_table_min];
- } else if (s >= cp932ext3_ucs_table_min && s < cp932ext3_ucs_table_max) { /* vendor ext3 (115ku - 119ku) */
- w = cp932ext3_ucs_table[s - cp932ext3_ucs_table_min];
- } else if (s >= (94*94) && s < (114*94)) { /* user (95ku - 114ku) */
- w = s - (94*94) + 0xe000;
}
- if (s >= (94*94) && s < 119*94) {
- if (filter->from->no_encoding == mbfl_no_encoding_sjis_docomo) {
- w = mbfilter_sjis_emoji_docomo2unicode(s, &snd);
- } else if (filter->from->no_encoding == mbfl_no_encoding_sjis_kddi) {
- w = mbfilter_sjis_emoji_kddi2unicode(s, &snd);
- } else if (filter->from->no_encoding == mbfl_no_encoding_sjis_sb) {
- w = mbfilter_sjis_emoji_sb2unicode(s, &snd);
+ /* Emoji */
+ if (filter->from == &mbfl_encoding_sjis_docomo && s >= mb_tbl_code2uni_docomo1_min && s <= mb_tbl_code2uni_docomo1_max) {
+ w = mbfilter_sjis_emoji_docomo2unicode(s, &snd);
+ if (snd > 0) {
+ CK((*filter->output_function)(snd, filter->data));
}
-
- if (w > 0 && snd > 0) {
+ } else if (filter->from == &mbfl_encoding_sjis_kddi && s >= mb_tbl_code2uni_kddi1_min && s <= mb_tbl_code2uni_kddi2_max) {
+ w = mbfilter_sjis_emoji_kddi2unicode(s, &snd);
+ if (snd > 0) {
+ CK((*filter->output_function)(snd, filter->data));
+ }
+ } else if (filter->from == &mbfl_encoding_sjis_sb && s >= mb_tbl_code2uni_sb1_min && s <= mb_tbl_code2uni_sb3_max) {
+ w = mbfilter_sjis_emoji_sb2unicode(s, &snd);
+ if (snd > 0) {
CK((*filter->output_function)(snd, filter->data));
}
}
+
+ if (w == 0) {
+ if (s >= cp932ext3_ucs_table_min && s < cp932ext3_ucs_table_max) { /* vendor ext3 (115ku - 119ku) */
+ w = cp932ext3_ucs_table[s - cp932ext3_ucs_table_min];
+ } else if (s >= (94*94) && s < (114*94)) { /* user (95ku - 114ku) */
+ w = s - (94*94) + 0xe000;
+ }
+ }
}
if (w <= 0) {
- w = (s1 << 8) | s2;
- w &= MBFL_WCSPLANE_MASK;
- w |= MBFL_WCSPLANE_WINCP932;
+ w = (s1 << 8) | s2 | MBFL_WCSPLANE_WINCP932;
}
CK((*filter->output_function)(w, filter->data));
- } else if ((c >= 0 && c < 0x21) || c == 0x7f) { /* CTLs */
- CK((*filter->output_function)(c, filter->data));
} else {
- w = (c1 << 8) | c;
- w &= MBFL_WCSGROUP_MASK;
- w |= MBFL_WCSGROUP_THROUGH;
- CK((*filter->output_function)(w, filter->data));
+ CK((*filter->output_function)((c1 << 8) | c | MBFL_WCSGROUP_THROUGH, filter->data));
}
break;
- /* ESC : Softbank Emoji */
+
+ /* ESC: Softbank Emoji */
case 2:
- if (filter->from->no_encoding == mbfl_no_encoding_sjis_sb &&
- c == 0x24) {
- filter->cache = c;
- filter->status++;
+ if (c == '$') {
+ filter->cache = c;
+ filter->status++;
} else {
- filter->cache = 0;
- filter->status = 0;
- CK((*filter->output_function)(0x1b, filter->data));
- goto retry;
+ CK((*filter->output_function)((filter->cache << 8) | c | MBFL_WCSGROUP_THROUGH, filter->data));
+ filter->status = filter->cache = 0;
}
break;
- /* ESC $ : Softbank Emoji */
+ /* ESC $: Softbank Emoji */
case 3:
- if (filter->from->no_encoding == mbfl_no_encoding_sjis_sb &&
- ((c >= 0x45 && c <= 0x47) || (c >= 0x4f && c <= 0x51))) {
- filter->cache = c;
- filter->status++;
+ if ((c >= 'E' && c <= 'G') || (c >= 'O' && c <= 'Q')) {
+ filter->cache = c;
+ filter->status++;
} else {
- filter->cache = 0;
- filter->status = 0;
- CK((*filter->output_function)(0x1b, filter->data));
- CK((*filter->output_function)(0x24, filter->data));
- goto retry;
+ CK((*filter->output_function)(0x1B2400 | c | MBFL_WCSGROUP_THROUGH, filter->data));
+ filter->status = filter->cache = 0;
}
break;
- /* ESC [GEFOPQ] : Softbank Emoji */
+ /* ESC $ [GEFOPQ]: Softbank Emoji */
case 4:
- w = 0;
- if (filter->from->no_encoding == mbfl_no_encoding_sjis_sb) {
- c1 = filter->cache;
-
- if (c == 0x0f) {
- w = c;
- filter->cache = 0;
- filter->status = 0;
+ c1 = filter->cache;
+ if (c == 0xF) { /* Terminate sequence of emoji */
+ filter->status = filter->cache = 0;
+ return c;
+ } else {
+ if (c1 == 'G' && c >= 0x21 && c <= 0x7a) {
+ s1 = (0x91 - 0x21) * 94;
+ } else if (c1 == 'E' && c >= 0x21 && c <= 0x7A) {
+ s1 = (0x8D - 0x21) * 94;
+ } else if (c1 == 'F' && c >= 0x21 && c <= 0x7A) {
+ s1 = (0x8E - 0x21) * 94;
+ } else if (c1 == 'O' && c >= 0x21 && c <= 0x6D) {
+ s1 = (0x92 - 0x21) * 94;
+ } else if (c1 == 'P' && c >= 0x21 && c <= 0x6C) {
+ s1 = (0x95 - 0x21) * 94;
+ } else if (c1 == 'Q' && c >= 0x21 && c <= 0x5E) {
+ s1 = (0x96 - 0x21) * 94;
} else {
- if (c1 == 0x47 && c >= 0x21 && c <= 0x7a) {
- s1 = 0x91; s2 = c;
- } else if (c1 == 0x45 && c >= 0x21 && c <= 0x7a) {
- s1 = 0x8d; s2 = c;
- } else if (c1 == 0x46 && c >= 0x21 && c <= 0x7a) {
- s1 = 0x8e; s2 = c;
- } else if (c1 == 0x4f && c >= 0x21 && c <= 0x6d) {
- s1 = 0x92; s2 = c;
- } else if (c1 == 0x50 && c >= 0x21 && c <= 0x6c) {
- s1 = 0x95; s2 = c;
- } else if (c1 == 0x51 && c >= 0x21 && c <= 0x5e) {
- s1 = 0x96; s2 = c;
- }
- s = (s1 - 0x21)*94 + s2 - 0x21;
- w = mbfilter_sjis_emoji_sb2unicode(s, &snd);
- if (w > 0) {
- if (snd > 0) {
- CK((*filter->output_function)(snd, filter->data));
- }
- CK((*filter->output_function)(w, filter->data));
+ CK((*filter->output_function)((c1 << 8) | c | MBFL_WCSGROUP_THROUGH, filter->data));
+ filter->status = filter->cache = 0;
+ return c;
+ }
+
+ w = mbfilter_sjis_emoji_sb2unicode(s1 + c - 0x21, &snd);
+ if (w > 0) {
+ if (snd > 0) {
+ CK((*filter->output_function)(snd, filter->data));
}
+ CK((*filter->output_function)(w, filter->data));
+ } else {
+ CK((*filter->output_function)((c1 << 8) | c | MBFL_WCSGROUP_THROUGH, filter->data));
+ filter->status = filter->cache = 0;
}
}
+ }
- if (w <= 0) {
- c1 = filter->cache;
- filter->cache = 0;
- filter->status = 0;
- CK((*filter->output_function)(0x1b, filter->data));
- CK((*filter->output_function)(0x24, filter->data));
- CK((*filter->output_function)(c1 & 0xff, filter->data));
- goto retry;
- }
- break;
+ return c;
+}
- default:
- filter->status = 0;
- break;
+static int mbfl_filt_conv_sjis_wchar_flush(mbfl_convert_filter *filter)
+{
+ if (filter->status && filter->status != 4) {
+ mbfl_filt_conv_illegal_output(filter->cache, filter);
}
- return c;
+ if (filter->flush_function) {
+ (*filter->flush_function)(filter->data);
+ }
+
+ return 0;
}
-/*
- * wchar => SJIS-win
- */
-int
-mbfl_filt_conv_wchar_sjis_mobile(int c, mbfl_convert_filter *filter)
+int mbfl_filt_conv_wchar_sjis_mobile(int c, mbfl_convert_filter *filter)
{
- int c1, c2, s1, s2;
+ int c1, c2, s1 = 0, s2 = 0;
- s1 = 0;
- s2 = 0;
if (c >= ucs_a1_jis_table_min && c < ucs_a1_jis_table_max) {
s1 = ucs_a1_jis_table[c - ucs_a1_jis_table_min];
} else if (c >= ucs_a2_jis_table_min && c < ucs_a2_jis_table_max) {
@@ -801,102 +737,83 @@ mbfl_filt_conv_wchar_sjis_mobile(int c, mbfl_convert_filter *filter)
s1 = ucs_i_jis_table[c - ucs_i_jis_table_min];
} else if (c >= ucs_r_jis_table_min && c < ucs_r_jis_table_max) {
s1 = ucs_r_jis_table[c - ucs_r_jis_table_min];
- } else if (c >= 0xe000 && c < (0xe000 + 20*94)) { /* user (95ku - 114ku) */
- s1 = c - 0xe000;
- c1 = s1/94 + 0x7f;
- c2 = s1%94 + 0x21;
+ } else if (c >= 0xE000 && c < (0xE000 + 20*94)) {
+ /* Private User Area (95ku - 114ku) */
+ s1 = c - 0xE000;
+ c1 = (s1 / 94) + 0x7F;
+ c2 = (s1 % 94) + 0x21;
s1 = (c1 << 8) | c2;
s2 = 1;
}
+
if (s1 <= 0) {
- c1 = c & ~MBFL_WCSPLANE_MASK;
- if (c1 == MBFL_WCSPLANE_WINCP932) {
- s1 = c & MBFL_WCSPLANE_MASK;
- s2 = 1;
- } else if (c1 == MBFL_WCSPLANE_JIS0208) {
- s1 = c & MBFL_WCSPLANE_MASK;
- } else if (c1 == MBFL_WCSPLANE_JIS0212) {
- s1 = c & MBFL_WCSPLANE_MASK;
- s1 |= 0x8080;
- } else if (c == 0xa5) { /* YEN SIGN */
- s1 = 0x216f; /* FULLWIDTH YEN SIGN */
- } else if (c == 0x203e) { /* OVER LINE */
- s1 = 0x2131; /* FULLWIDTH MACRON */
- } else if (c == 0xff3c) { /* FULLWIDTH REVERSE SOLIDUS */
+ if (c == 0xA5) { /* YEN SIGN */
+ s1 = 0x216F; /* FULLWIDTH YEN SIGN */
+ } else if (c == 0xFF3c) { /* FULLWIDTH REVERSE SOLIDUS */
s1 = 0x2140;
- } else if (c == 0xff5e) { /* FULLWIDTH TILDE */
- s1 = 0x2141;
- } else if (c == 0x2225) { /* PARALLEL TO */
+ } else if (c == 0x2225) { /* PARALLEL TO */
s1 = 0x2142;
- } else if (c == 0xff0d) { /* FULLWIDTH HYPHEN-MINUS */
- s1 = 0x215d;
- } else if (c == 0xffe0) { /* FULLWIDTH CENT SIGN */
+ } else if (c == 0xFF0D) { /* FULLWIDTH HYPHEN-MINUS */
+ s1 = 0x215D;
+ } else if (c == 0xFFE0) { /* FULLWIDTH CENT SIGN */
s1 = 0x2171;
- } else if (c == 0xffe1) { /* FULLWIDTH POUND SIGN */
+ } else if (c == 0xFFE1) { /* FULLWIDTH POUND SIGN */
s1 = 0x2172;
- } else if (c == 0xffe2) { /* FULLWIDTH NOT SIGN */
- s1 = 0x224c;
+ } else if (c == 0xFFE2) { /* FULLWIDTH NOT SIGN */
+ s1 = 0x224C;
}
}
if ((s1 <= 0) || (s1 >= 0x8080 && s2 == 0)) { /* not found or X 0212 */
s1 = -1;
- c1 = 0;
- c2 = cp932ext1_ucs_table_max - cp932ext1_ucs_table_min;
- while (c1 < c2) { /* CP932 vendor ext1 (13ku) */
+
+ /* CP932 vendor ext1 (13ku) */
+ for (c1 = 0; c1 < cp932ext1_ucs_table_max - cp932ext1_ucs_table_min; c1++) {
if (c == cp932ext1_ucs_table[c1]) {
- s1 = ((c1/94 + 0x2d) << 8) + (c1%94 + 0x21);
+ s1 = (((c1 / 94) + 0x2D) << 8) + (c1 % 94) + 0x21;
break;
}
- c1++;
}
+
if (s1 <= 0) {
- c1 = 0;
- c2 = cp932ext2_ucs_table_max - cp932ext2_ucs_table_min;
- while (c1 < c2) { /* CP932 vendor ext2 (115ku - 119ku) */
+ /* CP932 vendor ext2 (115ku - 119ku) */
+ for (c1 = 0; c1 < cp932ext2_ucs_table_max - cp932ext2_ucs_table_min; c1++) {
if (c == cp932ext2_ucs_table[c1]) {
- s1 = ((c1/94 + 0x93) << 8) + (c1%94 + 0x21);
+ s1 = (((c1 / 94) + 0x79) << 8) + (c1 % 94) + 0x21;
break;
}
- c1++;
}
}
if (s1 <= 0) {
- c1 = 0;
- c2 = cp932ext3_ucs_table_max - cp932ext3_ucs_table_min;
- while (c1 < c2) { /* CP932 vendor ext3 (115ku - 119ku) */
+ /* CP932 vendor ext3 (115ku - 119ku) */
+ for (c1 = 0; c1 < cp932ext3_ucs_table_max - cp932ext3_ucs_table_min; c1++) {
if (c == cp932ext3_ucs_table[c1]) {
- s1 = ((c1/94 + 0x93) << 8) + (c1%94 + 0x21);
+ s1 = (((c1 / 94) + 0x93) << 8) + (c1 % 94) + 0x21;
break;
}
- c1++;
}
}
+
if (c == 0) {
s1 = 0;
- } else if (s1 <= 0) {
- s1 = -1;
}
}
- if ((filter->to->no_encoding == mbfl_no_encoding_sjis_docomo &&
- mbfilter_unicode2sjis_emoji_docomo(c, &s1, filter) > 0) ||
- (filter->to->no_encoding == mbfl_no_encoding_sjis_kddi &&
- mbfilter_unicode2sjis_emoji_kddi(c, &s1, filter) > 0) ||
- (filter->to->no_encoding == mbfl_no_encoding_sjis_sb &&
- mbfilter_unicode2sjis_emoji_sb(c, &s1, filter) > 0 )) {
+ if ((filter->to == &mbfl_encoding_sjis_docomo && mbfilter_unicode2sjis_emoji_docomo(c, &s1, filter)) ||
+ (filter->to == &mbfl_encoding_sjis_kddi && mbfilter_unicode2sjis_emoji_kddi(c, &s1, filter)) ||
+ (filter->to == &mbfl_encoding_sjis_sb && mbfilter_unicode2sjis_emoji_sb(c, &s1, filter))) {
CODE2JIS(c1,c2,s1,s2);
}
- if (filter->status == 1 && filter->cache > 0) {
+ if (filter->status) {
return c;
}
if (s1 >= 0) {
- if (s1 < 0x100) { /* latin or kana */
+ if (s1 < 0x100) { /* Latin/Kana */
CK((*filter->output_function)(s1, filter->data));
- } else { /* kanji */
+ } else { /* Kanji */
c1 = (s1 >> 8) & 0xff;
c2 = s1 & 0xff;
SJIS_ENCODE(c1, c2, s1, s2);
@@ -910,18 +827,15 @@ mbfl_filt_conv_wchar_sjis_mobile(int c, mbfl_convert_filter *filter)
return c;
}
-int
-mbfl_filt_conv_sjis_mobile_flush(mbfl_convert_filter *filter)
+int mbfl_filt_conv_sjis_mobile_flush(mbfl_convert_filter *filter)
{
int c1 = filter->cache;
- if (filter->status == 1 && (c1 == 0x0023 || (c1 >= 0x0030 && c1<=0x0039))) {
+ if (filter->status == 1 && (c1 == '#' || (c1 >= '0' && c1 <= '9'))) {
CK((*filter->output_function)(c1, filter->data));
}
- filter->status = 0;
- filter->cache = 0;
- if (filter->flush_function != NULL) {
- return (*filter->flush_function)(filter->data);
+ if (filter->flush_function) {
+ (*filter->flush_function)(filter->data);
}
return 0;