move replace_all function to base/string.h
[enigma2.git] / lib / base / estring.cpp
1 #include <string>
2 #include <ctype.h>
3 #include <limits.h>
4 #include <lib/base/eerror.h>
5 #include <lib/base/encoding.h>
6 #include <lib/base/estring.h>
7
8 std::string buildShortName( const std::string &str )
9 {
10         std::string tmp;
11         static char stropen[3] = { 0xc2, 0x86, 0x00 };
12         static char strclose[3] = { 0xc2, 0x87, 0x00 };
13         size_t open=std::string::npos-1;
14         while ( (open = str.find(stropen, open+2)) != std::string::npos )
15         {
16                 size_t close = str.find(strclose, open);
17                 if ( close != std::string::npos )
18                         tmp+=str.substr( open+2, close-(open+2) );
19         }
20         return tmp.length() ? tmp : str;
21 }
22
23 std::string getNum(int val, int sys)
24 {
25 //      Returns a string that contain the value val as string
26 //      if sys == 16 than hexadezimal if sys == 10 than decimal
27         char buf[12];
28
29         if (sys == 10)
30                 snprintf(buf, 12, "%i", val);
31         else if (sys == 16)
32                 snprintf(buf, 12, "%X", val);           
33         
34         std::string res;
35         res.assign(buf);
36         return res;
37 }
38
39                 // 8859-x to ucs-16 coding tables. taken from www.unicode.org/Public/MAPPINGS/ISO8859/
40
41 static unsigned long c88592[96]={
42 0x00A0, 0x0104, 0x02D8, 0x0141, 0x00A4, 0x013D, 0x015A, 0x00A7, 0x00A8, 0x0160, 0x015E, 0x0164, 0x0179, 0x00AD, 0x017D, 0x017B,
43 0x00B0, 0x0105, 0x02DB, 0x0142, 0x00B4, 0x013E, 0x015B, 0x02C7, 0x00B8, 0x0161, 0x015F, 0x0165, 0x017A, 0x02DD, 0x017E, 0x017C,
44 0x0154, 0x00C1, 0x00C2, 0x0102, 0x00C4, 0x0139, 0x0106, 0x00C7, 0x010C, 0x00C9, 0x0118, 0x00CB, 0x011A, 0x00CD, 0x00CE, 0x010E,
45 0x0110, 0x0143, 0x0147, 0x00D3, 0x00D4, 0x0150, 0x00D6, 0x00D7, 0x0158, 0x016E, 0x00DA, 0x0170, 0x00DC, 0x00DD, 0x0162, 0x00DF,
46 0x0155, 0x00E1, 0x00E2, 0x0103, 0x00E4, 0x013A, 0x0107, 0x00E7, 0x010D, 0x00E9, 0x0119, 0x00EB, 0x011B, 0x00ED, 0x00EE, 0x010F,
47 0x0111, 0x0144, 0x0148, 0x00F3, 0x00F4, 0x0151, 0x00F6, 0x00F7, 0x0159, 0x016F, 0x00FA, 0x0171, 0x00FC, 0x00FD, 0x0163, 0x02D9};
48
49 static unsigned long c88593[96]={
50 0x00A0, 0x0126, 0x02D8, 0x00A3, 0x00A4, 0x0000, 0x0124, 0x00A7, 0x00A8, 0x0130, 0x015E, 0x011E, 0x0134, 0x00AD, 0x0000, 0x017B,
51 0x00B0, 0x0127, 0x00B2, 0x00B3, 0x00B4, 0x00B5, 0x0125, 0x00B7, 0x00B8, 0x0131, 0x015F, 0x011F, 0x0135, 0x00BD, 0x0000, 0x017C,
52 0x00C0, 0x00C1, 0x00C2, 0x0000, 0x00C4, 0x010A, 0x0108, 0x00C7, 0x00C8, 0x00C9, 0x00CA, 0x00CB, 0x00CC, 0x00CD, 0x00CE, 0x00CF,
53 0x0000, 0x00D1, 0x00D2, 0x00D3, 0x00D4, 0x0120, 0x00D6, 0x00D7, 0x011C, 0x00D9, 0x00DA, 0x00DB, 0x00DC, 0x016C, 0x015C, 0x00DF,
54 0x00E0, 0x00E1, 0x00E2, 0x0000, 0x00E4, 0x010B, 0x0109, 0x00E7, 0x00E8, 0x00E9, 0x00EA, 0x00EB, 0x00EC, 0x00ED, 0x00EE, 0x00EF,
55 0x0000, 0x00F1, 0x00F2, 0x00F3, 0x00F4, 0x0121, 0x00F6, 0x00F7, 0x011D, 0x00F9, 0x00FA, 0x00FB, 0x00FC, 0x016D, 0x015D, 0x02D9};
56
57 static unsigned long c88594[96]={
58 0x00A0, 0x0104, 0x0138, 0x0156, 0x00A4, 0x0128, 0x013B, 0x00A7, 0x00A8, 0x0160, 0x0112, 0x0122, 0x0166, 0x00AD, 0x017D, 0x00AF,
59 0x00B0, 0x0105, 0x02DB, 0x0157, 0x00B4, 0x0129, 0x013C, 0x02C7, 0x00B8, 0x0161, 0x0113, 0x0123, 0x0167, 0x014A, 0x017E, 0x014B,
60 0x0100, 0x00C1, 0x00C2, 0x00C3, 0x00C4, 0x00C5, 0x00C6, 0x012E, 0x010C, 0x00C9, 0x0118, 0x00CB, 0x0116, 0x00CD, 0x00CE, 0x012A,
61 0x0110, 0x0145, 0x014C, 0x0136, 0x00D4, 0x00D5, 0x00D6, 0x00D7, 0x00D8, 0x0172, 0x00DA, 0x00DB, 0x00DC, 0x0168, 0x016A, 0x00DF,
62 0x0101, 0x00E1, 0x00E2, 0x00E3, 0x00E4, 0x00E5, 0x00E6, 0x012F, 0x010D, 0x00E9, 0x0119, 0x00EB, 0x0117, 0x00ED, 0x00EE, 0x012B,
63 0x0111, 0x0146, 0x014D, 0x0137, 0x00F4, 0x00F5, 0x00F6, 0x00F7, 0x00F8, 0x0173, 0x00FA, 0x00FB, 0x00FC, 0x0169, 0x016B, 0x02D9};
64
65 static unsigned long c88595[96]={
66 0x00A0, 0x0401, 0x0402, 0x0403, 0x0404, 0x0405, 0x0406, 0x0407, 0x0408, 0x0409, 0x040A, 0x040B, 0x040C, 0x00AD, 0x040E, 0x040F,
67 0x0410, 0x0411, 0x0412, 0x0413, 0x0414, 0x0415, 0x0416, 0x0417, 0x0418, 0x0419, 0x041A, 0x041B, 0x041C, 0x041D, 0x041E, 0x041F,
68 0x0420, 0x0421, 0x0422, 0x0423, 0x0424, 0x0425, 0x0426, 0x0427, 0x0428, 0x0429, 0x042A, 0x042B, 0x042C, 0x042D, 0x042E, 0x042F,
69 0x0430, 0x0431, 0x0432, 0x0433, 0x0434, 0x0435, 0x0436, 0x0437, 0x0438, 0x0439, 0x043A, 0x043B, 0x043C, 0x043D, 0x043E, 0x043F,
70 0x0440, 0x0441, 0x0442, 0x0443, 0x0444, 0x0445, 0x0446, 0x0447, 0x0448, 0x0449, 0x044A, 0x044B, 0x044C, 0x044D, 0x044E, 0x044F,
71 0x2116, 0x0451, 0x0452, 0x0453, 0x0454, 0x0455, 0x0456, 0x0457, 0x0458, 0x0459, 0x045A, 0x045B, 0x045C, 0x00A7, 0x045E, 0x045F};
72
73 static unsigned long c88596[96]={
74 0x00A0, 0x0000, 0x0000, 0x0000, 0x00A4, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x060C, 0x00AD, 0x0000, 0x0000,
75 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x061B, 0x0000, 0x0000, 0x0000, 0x061F,
76 0x0000, 0x0621, 0x0622, 0x0623, 0x0624, 0x0625, 0x0626, 0x0627, 0x0628, 0x0629, 0x062A, 0x062B, 0x062C, 0x062D, 0x062E, 0x062F,
77 0x0630, 0x0631, 0x0632, 0x0633, 0x0634, 0x0635, 0x0636, 0x0637, 0x0638, 0x0639, 0x063A, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000,
78 0x0640, 0x0641, 0x0642, 0x0643, 0x0644, 0x0645, 0x0646, 0x0647, 0x0648, 0x0649, 0x064A, 0x064B, 0x064C, 0x064D, 0x064E, 0x064F,
79 0x0650, 0x0651, 0x0652, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000};
80
81 static unsigned long c88597[96]={
82 0x00A0, 0x2018, 0x2019, 0x00A3, 0x20AC, 0x20AF, 0x00A6, 0x00A7, 0x00A8, 0x00A9, 0x037A, 0x00AB, 0x00AC, 0x00AD, 0x0000, 0x2015,
83 0x00B0, 0x00B1, 0x00B2, 0x00B3, 0x0384, 0x0385, 0x0386, 0x00B7, 0x0388, 0x0389, 0x038A, 0x00BB, 0x038C, 0x00BD, 0x038E, 0x038F,
84 0x0390, 0x0391, 0x0392, 0x0393, 0x0394, 0x0395, 0x0396, 0x0397, 0x0398, 0x0399, 0x039A, 0x039B, 0x039C, 0x039D, 0x039E, 0x039F,
85 0x03A0, 0x03A1, 0x0000, 0x03A3, 0x03A4, 0x03A5, 0x03A6, 0x03A7, 0x03A8, 0x03A9, 0x03AA, 0x03AB, 0x03AC, 0x03AD, 0x03AE, 0x03AF,
86 0x03B0, 0x03B1, 0x03B2, 0x03B3, 0x03B4, 0x03B5, 0x03B6, 0x03B7, 0x03B8, 0x03B9, 0x03BA, 0x03BB, 0x03BC, 0x03BD, 0x03BE, 0x03BF,
87 0x03C0, 0x03C1, 0x03C2, 0x03C3, 0x03C4, 0x03C5, 0x03C6, 0x03C7, 0x03C8, 0x03C9, 0x03CA, 0x03CB, 0x03CC, 0x03CD, 0x03CE, 0x0000};
88
89 static unsigned long c88598[96]={
90 0x00A0, 0x0000, 0x00A2, 0x00A3, 0x00A4, 0x00A5, 0x00A6, 0x00A7, 0x00A8, 0x00A9, 0x00D7, 0x00AB, 0x00AC, 0x00AD, 0x00AE, 0x00AF,
91 0x00B0, 0x00B1, 0x00B2, 0x00B3, 0x00B4, 0x00B5, 0x00B6, 0x00B7, 0x00B8, 0x00B9, 0x00F7, 0x00BB, 0x00BC, 0x00BD, 0x00BE, 0x0000,
92 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000,
93 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x2017,
94 0x05D0, 0x05D1, 0x05D2, 0x05D3, 0x05D4, 0x05D5, 0x05D6, 0x05D7, 0x05D8, 0x05D9, 0x05DA, 0x05DB, 0x05DC, 0x05DD, 0x05DE, 0x05DF,
95 0x05E0, 0x05E1, 0x05E2, 0x05E3, 0x05E4, 0x05E5, 0x05E6, 0x05E7, 0x05E8, 0x05E9, 0x05EA, 0x0000, 0x0000, 0x200E, 0x200F, 0x0000};
96
97 static unsigned long c88599[96]={
98 0x00A0, 0x00A1, 0x00A2, 0x00A3, 0x00A4, 0x00A5, 0x00A6, 0x00A7, 0x00A8, 0x00A9, 0x00AA, 0x00AB, 0x00AC, 0x00AD, 0x00AE, 0x00AF,
99 0x00B0, 0x00B1, 0x00B2, 0x00B3, 0x00B4, 0x00B5, 0x00B6, 0x00B7, 0x00B8, 0x00B9, 0x00BA, 0x00BB, 0x00BC, 0x00BD, 0x00BE, 0x00BF,
100 0x00C0, 0x00C1, 0x00C2, 0x00C3, 0x00C4, 0x00C5, 0x00C6, 0x00C7, 0x00C8, 0x00C9, 0x00CA, 0x00CB, 0x00CC, 0x00CD, 0x00CE, 0x00CF,
101 0x011E, 0x00D1, 0x00D2, 0x00D3, 0x00D4, 0x00D5, 0x00D6, 0x00D7, 0x00D8, 0x00D9, 0x00DA, 0x00DB, 0x00DC, 0x0130, 0x015E, 0x00DF,
102 0x00E0, 0x00E1, 0x00E2, 0x00E3, 0x00E4, 0x00E5, 0x00E6, 0x00E7, 0x00E8, 0x00E9, 0x00EA, 0x00EB, 0x00EC, 0x00ED, 0x00EE, 0x00EF,
103 0x011F, 0x00F1, 0x00F2, 0x00F3, 0x00F4, 0x00F5, 0x00F6, 0x00F7, 0x00F8, 0x00F9, 0x00FA, 0x00FB, 0x00FC, 0x0131, 0x015F, 0x00FF};
104
105 static unsigned long c885910[96]={
106 0x00A0, 0x0104, 0x0112, 0x0122, 0x012A, 0x0128, 0x0136, 0x00A7, 0x013B, 0x0110, 0x0160, 0x0166, 0x017D, 0x00AD, 0x016A, 0x014A,
107 0x00B0, 0x0105, 0x0113, 0x0123, 0x012B, 0x0129, 0x0137, 0x00B7, 0x013C, 0x0111, 0x0161, 0x0167, 0x017E, 0x2015, 0x016B, 0x014B,
108 0x0100, 0x00C1, 0x00C2, 0x00C3, 0x00C4, 0x00C5, 0x00C6, 0x012E, 0x010C, 0x00C9, 0x0118, 0x00CB, 0x0116, 0x00CD, 0x00CE, 0x00CF,
109 0x00D0, 0x0145, 0x014C, 0x00D3, 0x00D4, 0x00D5, 0x00D6, 0x0168, 0x00D8, 0x0172, 0x00DA, 0x00DB, 0x00DC, 0x00DD, 0x00DE, 0x00DF,
110 0x0101, 0x00E1, 0x00E2, 0x00E3, 0x00E4, 0x00E5, 0x00E6, 0x012F, 0x010D, 0x00E9, 0x0119, 0x00EB, 0x0117, 0x00ED, 0x00EE, 0x00EF,
111 0x00F0, 0x0146, 0x014D, 0x00F3, 0x00F4, 0x00F5, 0x00F6, 0x0169, 0x00F8, 0x0173, 0x00FA, 0x00FB, 0x00FC, 0x00FD, 0x00FE, 0x0138};
112
113 static unsigned long c885911[96]={
114 0x00A0, 0x0E01, 0x0E02, 0x0E03, 0x0E04, 0x0E05, 0x0E06, 0x0E07, 0x0E08, 0x0E09, 0x0E0A, 0x0E0B, 0x0E0C, 0x0E0D, 0x0E0E, 0x0E0F,
115 0x0E10, 0x0E11, 0x0E12, 0x0E13, 0x0E14, 0x0E15, 0x0E16, 0x0E17, 0x0E18, 0x0E19, 0x0E1A, 0x0E1B, 0x0E1C, 0x0E1D, 0x0E1E, 0x0E1F,
116 0x0E20, 0x0E21, 0x0E22, 0x0E23, 0x0E24, 0x0E25, 0x0E26, 0x0E27, 0x0E28, 0x0E29, 0x0E2A, 0x0E2B, 0x0E2C, 0x0E2D, 0x0E2E, 0x0E2F,
117 0x0E30, 0x0E31, 0x0E32, 0x0E33, 0x0E34, 0x0E35, 0x0E36, 0x0E37, 0x0E38, 0x0E39, 0x0E3A, 0x0000, 0x0000, 0x0000, 0x0000, 0x0E3F,
118 0x0E40, 0x0E41, 0x0E42, 0x0E43, 0x0E44, 0x0E45, 0x0E46, 0x0E47, 0x0E48, 0x0E49, 0x0E4A, 0x0E4B, 0x0E4C, 0x0E4D, 0x0E4E, 0x0E4F,
119 0x0E50, 0x0E51, 0x0E52, 0x0E53, 0x0E54, 0x0E55, 0x0E56, 0x0E57, 0x0E58, 0x0E59, 0x0E5A, 0x0E5B, 0x0000, 0x0000, 0x0000, 0x0000};
120
121 static unsigned long c885913[96]={
122 0x00A0, 0x201D, 0x00A2, 0x00A3, 0x00A4, 0x201E, 0x00A6, 0x00A7, 0x00D8, 0x00A9, 0x0156, 0x00AB, 0x00AC, 0x00AD, 0x00AE, 0x00C6,
123 0x00B0, 0x00B1, 0x00B2, 0x00B3, 0x201C, 0x00B5, 0x00B6, 0x00B7, 0x00F8, 0x00B9, 0x0157, 0x00BB, 0x00BC, 0x00BD, 0x00BE, 0x00E6,
124 0x0104, 0x012E, 0x0100, 0x0106, 0x00C4, 0x00C5, 0x0118, 0x0112, 0x010C, 0x00C9, 0x0179, 0x0116, 0x0122, 0x0136, 0x012A, 0x013B,
125 0x0160, 0x0143, 0x0145, 0x00D3, 0x014C, 0x00D5, 0x00D6, 0x00D7, 0x0172, 0x0141, 0x015A, 0x016A, 0x00DC, 0x017B, 0x017D, 0x00DF,
126 0x0105, 0x012F, 0x0101, 0x0107, 0x00E4, 0x00E5, 0x0119, 0x0113, 0x010D, 0x00E9, 0x017A, 0x0117, 0x0123, 0x0137, 0x012B, 0x013C,
127 0x0161, 0x0144, 0x0146, 0x00F3, 0x014D, 0x00F5, 0x00F6, 0x00F7, 0x0173, 0x0142, 0x015B, 0x016B, 0x00FC, 0x017C, 0x017E, 0x2019};
128
129 static unsigned long c885914[96]={
130 0x00A0, 0x1E02, 0x1E03, 0x00A3, 0x010A, 0x010B, 0x1E0A, 0x00A7, 0x1E80, 0x00A9, 0x1E82, 0x1E0B, 0x1EF2, 0x00AD, 0x00AE, 0x0178,
131 0x1E1E, 0x1E1F, 0x0120, 0x0121, 0x1E40, 0x1E41, 0x00B6, 0x1E56, 0x1E81, 0x1E57, 0x1E83, 0x1E60, 0x1EF3, 0x1E84, 0x1E85, 0x1E61,
132 0x00C0, 0x00C1, 0x00C2, 0x00C3, 0x00C4, 0x00C5, 0x00C6, 0x00C7, 0x00C8, 0x00C9, 0x00CA, 0x00CB, 0x00CC, 0x00CD, 0x00CE, 0x00CF,
133 0x0174, 0x00D1, 0x00D2, 0x00D3, 0x00D4, 0x00D5, 0x00D6, 0x1E6A, 0x00D8, 0x00D9, 0x00DA, 0x00DB, 0x00DC, 0x00DD, 0x0176, 0x00DF,
134 0x00E0, 0x00E1, 0x00E2, 0x00E3, 0x00E4, 0x00E5, 0x00E6, 0x00E7, 0x00E8, 0x00E9, 0x00EA, 0x00EB, 0x00EC, 0x00ED, 0x00EE, 0x00EF,
135 0x0175, 0x00F1, 0x00F2, 0x00F3, 0x00F4, 0x00F5, 0x00F6, 0x1E6B, 0x00F8, 0x00F9, 0x00FA, 0x00FB, 0x00FC, 0x00FD, 0x0177, 0x00FF};
136
137 static unsigned long c885915[96]={
138 0x00A0, 0x00A1, 0x00A2, 0x00A3, 0x20AC, 0x00A5, 0x0160, 0x00A7, 0x0161, 0x00A9, 0x00AA, 0x00AB, 0x00AC, 0x00AD, 0x00AE, 0x00AF,
139 0x00B0, 0x00B1, 0x00B2, 0x00B3, 0x017D, 0x00B5, 0x00B6, 0x00B7, 0x017E, 0x00B9, 0x00BA, 0x00BB, 0x0152, 0x0153, 0x0178, 0x00BF,
140 0x00C0, 0x00C1, 0x00C2, 0x00C3, 0x00C4, 0x00C5, 0x00C6, 0x00C7, 0x00C8, 0x00C9, 0x00CA, 0x00CB, 0x00CC, 0x00CD, 0x00CE, 0x00CF,
141 0x00D0, 0x00D1, 0x00D2, 0x00D3, 0x00D4, 0x00D5, 0x00D6, 0x00D7, 0x00D8, 0x00D9, 0x00DA, 0x00DB, 0x00DC, 0x00DD, 0x00DE, 0x00DF,
142 0x00E0, 0x00E1, 0x00E2, 0x00E3, 0x00E4, 0x00E5, 0x00E6, 0x00E7, 0x00E8, 0x00E9, 0x00EA, 0x00EB, 0x00EC, 0x00ED, 0x00EE, 0x00EF,
143 0x00F0, 0x00F1, 0x00F2, 0x00F3, 0x00F4, 0x00F5, 0x00F6, 0x00F7, 0x00F8, 0x00F9, 0x00FA, 0x00FB, 0x00FC, 0x00FD, 0x00FE, 0x00FF};
144
145 static unsigned long c885916[96]={
146 0x00A0, 0x0104, 0x0105, 0x0141, 0x20AC, 0x201E, 0x0160, 0x00A7, 0x0161, 0x00A9, 0x0218, 0x00AB, 0x0179, 0x00AD, 0x017A, 0x017B,
147 0x00B0, 0x00B1, 0x010C, 0x0142, 0x017D, 0x201D, 0x00B6, 0x00B7, 0x017E, 0x010D, 0x0219, 0x00BB, 0x0152, 0x0153, 0x0178, 0x017C,
148 0x00C0, 0x00C1, 0x00C2, 0x0102, 0x00C4, 0x0106, 0x00C6, 0x00C7, 0x00C8, 0x00C9, 0x00CA, 0x00CB, 0x00CC, 0x00CD, 0x00CE, 0x00CF,
149 0x0110, 0x0143, 0x00D2, 0x00D3, 0x00D4, 0x0150, 0x00D6, 0x015A, 0x0170, 0x00D9, 0x00DA, 0x00DB, 0x00DC, 0x0118, 0x021A, 0x00DF,
150 0x00E0, 0x00E1, 0x00E2, 0x0103, 0x00E4, 0x0107, 0x00E6, 0x00E7, 0x00E8, 0x00E9, 0x00EA, 0x00EB, 0x00EC, 0x00ED, 0x00EE, 0x00EF,
151 0x0111, 0x0144, 0x00F2, 0x00F3, 0x00F4, 0x0151, 0x00F6, 0x015B, 0x0171, 0x00F9, 0x00FA, 0x00FB, 0x00FC, 0x0119, 0x021B, 0x00FF};
152
153 // Two Char Mapping ( many polish services and UPC Direct/HBO services)
154 // get from http://mitglied.lycos.de/buran/charsets/videotex-suppl.html
155 static inline unsigned int doVideoTexSuppl(int c1, int c2)
156 {
157         switch (c1)
158         {
159                 case 0xC1: // grave
160                         switch (c2)
161                         {
162                                 case 0x61: return 224;                          case 0x41: return 192;
163                                 case 0x65: return 232;                          case 0x45: return 200;
164                                 case 0x69: return 236;                          case 0x49: return 204;
165                                 case 0x6f: return 242;                          case 0x4f: return 210;
166                                 case 0x75: return 249;                          case 0x55: return 217;
167                                 default: return 0;
168                         }
169                 case 0xC2: // acute
170                         switch (c2)
171                         {
172                                 case 0x61: return 225;                          case 0x41: return 193;
173                                 case 0x65: return 233;                          case 0x45: return 201;
174                                 case 0x69: return 237;                          case 0x49: return 205;
175                                 case 0x6f: return 243;                          case 0x4f: return 211;
176                                 case 0x75: return 250;                          case 0x55: return 218;
177                                 case 0x79: return 253;                          case 0x59: return 221;
178                                 case 0x63: return 263;                          case 0x43: return 262;
179                                 case 0x6c: return 314;                          case 0x4c: return 313;
180                                 case 0x6e: return 324;                          case 0x4e: return 323;
181                                 case 0x72: return 341;                          case 0x52: return 340;
182                                 case 0x73: return 347;                          case 0x53: return 346;
183                                 case 0x7a: return 378;                          case 0x5a: return 377;
184                                 default: return 0;
185                         }
186                 case 0xC3: // cedilla
187                         switch (c2)
188                         {
189                                 case 0x61: return 226;                          case 0x41: return 194;
190                                 case 0x65: return 234;                          case 0x45: return 202;
191                                 case 0x69: return 238;                          case 0x49: return 206;
192                                 case 0x6f: return 244;                          case 0x4f: return 212;
193                                 case 0x75: return 251;                          case 0x55: return 219;
194                                 case 0x79: return 375;                          case 0x59: return 374;
195                                 case 0x63: return 265;                          case 0x43: return 264;
196                                 case 0x67: return 285;                          case 0x47: return 284;
197                                 case 0x68: return 293;                          case 0x48: return 292;
198                                 case 0x6a: return 309;                          case 0x4a: return 308;
199                                 case 0x73: return 349;                          case 0x53: return 348;
200                                 case 0x77: return 373;                          case 0x57: return 372;
201                                 default: return 0;
202                         }
203                 case 0xC4: // tilde
204                         switch (c2)
205                         {
206                                 case 0x61: return 227;                          case 0x41: return 195;
207                                 case 0x6e: return 241;                          case 0x4e: return 209;
208                                 case 0x69: return 297;                          case 0x49: return 296;
209                                 case 0x6f: return 245;                          case 0x4f: return 213;
210                                 case 0x75: return 361;                          case 0x55: return 360;
211                                 default: return 0;
212                         }
213                 case 0xC6: // breve
214                         switch (c2)
215                         {
216                                 case 0x61: return 259;                          case 0x41: return 258;
217                                 case 0x67: return 287;                          case 0x47: return 286;
218                                 case 0x75: return 365;                          case 0x55: return 364;
219                                 default: return 0;
220                         }
221                 case 0xC7: // dot above
222                         switch (c2)
223                         {
224                                 case 0x63: return 267;                          case 0x43: return 266;
225                                 case 0x65: return 279;                          case 0x45: return 278;
226                                 case 0x67: return 289;                          case 0x47: return 288;
227                                 case 0x49: return 304;                          case 0x7a: return 380;
228                                 case 0x5a: return 379;
229                                 default: return 0;
230                         }
231                 case 0xC8: // diaeresis
232                         switch (c2)
233                         {
234                                 case 0x61: return 228;                          case 0x41: return 196;
235                                 case 0x65: return 235;                          case 0x45: return 203;
236                                 case 0x69: return 239;                          case 0x49: return 207;
237                                 case 0x6f: return 246;                          case 0x4f: return 214;
238                                 case 0x75: return 252;                          case 0x55: return 220;
239                                 case 0x79: return 255;                          case 0x59: return 376;
240                                 default: return 0;
241                                 }
242                 case 0xCA: // ring above
243                         switch (c2)
244                         {
245                                 case 0x61: return 229;                          case 0x41: return 197;
246                                 case 0x75: return 367;                          case 0x55: return 366;
247                                 default: return 0;
248                         }
249                 case 0xCB: // cedilla
250                         switch (c2)
251                         {
252                                 case 0x63: return 231;                          case 0x43: return 199;
253                                 case 0x67: return 291;                          case 0x47: return 290;
254                                 case 0x6b: return 311;                          case 0x4b: return 310;
255                                 case 0x6c: return 316;                          case 0x4c: return 315;
256                                 case 0x6e: return 326;                          case 0x4e: return 325;
257                                 case 0x72: return 343;                          case 0x52: return 342;
258                                 case 0x73: return 351;                          case 0x53: return 350;
259                                 case 0x74: return 355;                          case 0x54: return 354;
260                                 default: return 0;
261                         }
262                 case 0xCD: // double acute accent
263                         switch (c2)
264                         {
265                                 case 0x6f: return 337;                          case 0x4f: return 336;
266                                 case 0x75: return 369;                          case 0x55: return 368;
267                                 default: return 0;
268                         }
269                 case 0xCE: // ogonek
270                         switch (c2)
271                         {
272                                 case 0x61: return 261;                          case 0x41: return 260;
273                                 case 0x65: return 281;                          case 0x45: return 280;
274                                 case 0x69: return 303;                          case 0x49: return 302;
275                                 case 0x75: return 371;                          case 0x55: return 370;
276                                 default: return 0;
277                         }
278                 case 0xCF: // caron
279                         switch (c2)
280                         {
281                                 case 0x63: return 269;                          case 0x43: return 268;
282                                 case 0x64: return 271;                          case 0x44: return 270;
283                                 case 0x65: return 283;                          case 0x45: return 282;
284                                 case 0x6c: return 318;                          case 0x4c: return 317;
285                                 case 0x6e: return 328;                          case 0x4e: return 327;
286                                 case 0x72: return 345;                          case 0x52: return 344;
287                                 case 0x73: return 353;                          case 0x53: return 352;
288                                 case 0x74: return 357;                          case 0x54: return 356;
289                                 case 0x7a: return 382;                          case 0x5a: return 381;
290                                 default: return 0;
291                         }
292         }
293         return 0;
294 }
295
296 static inline unsigned int recode(unsigned char d, int cp)
297 {
298         if (d < 0xA0)
299                 return d;
300         switch (cp)
301         {
302         case 0:         // Latin1 <-> unicode mapping
303         case 1:         // 8859-1 <-> unicode mapping
304                 return d;
305         case 2:         // 8859-2 -> unicode mapping
306                 return c88592[d-0xA0];
307         case 3:         // 8859-3 -> unicode mapping
308                 return c88593[d-0xA0];
309         case 4:         // 8859-2 -> unicode mapping
310                 return c88594[d-0xA0];
311         case 5:         // 8859-5 -> unicode mapping
312                 return c88595[d-0xA0];
313         case 6:         // 8859-6 -> unicode mapping
314                 return c88596[d-0xA0];
315         case 7:         // 8859-7 -> unicode mapping
316                 return c88597[d-0xA0];
317         case 8:         // 8859-8 -> unicode mapping
318                 return c88598[d-0xA0];
319         case 9:         // 8859-9 -> unicode mapping
320                 return c88599[d-0xA0];
321         case 10:// 8859-10 -> unicode mapping
322                 return c885910[d-0xA0];
323         case 11:// 8859-11 -> unicode mapping
324                 return c885911[d-0xA0];
325 /*      case 12:// 8859-12 -> unicode mapping  // reserved for indian use..
326                 return c885912[d-0xA0];*/
327         case 13:// 8859-13 -> unicode mapping
328                 return c885913[d-0xA0];
329         case 14:// 8859-14 -> unicode mapping
330                 return c885914[d-0xA0];
331         case 15:// 8859-15 -> unicode mapping
332                 return c885915[d-0xA0];
333         case 16:// 8859-16 -> unicode mapping
334                 return c885916[d-0xA0];
335         default:
336                 return d;
337         }
338 }
339
340 std::string convertDVBUTF8(const unsigned char *data, int len, int table, int tsidonid)
341 {
342         if (!len)
343                 return "";
344
345         int i=0, t=0;
346
347         if ( tsidonid )
348                 encodingHandler.getTransponderDefaultMapping(tsidonid, table);
349
350         switch(data[0])
351         {
352                 case 1 ... 11:
353                         table=data[i++]+4;
354 //                      eDebug("(1..11)text encoded in ISO-8859-%d",table);
355                         break;
356                 case 0x10:
357                 {
358 //                      eDebug("(0x10)text encoded in ISO-8859-%d",n);
359                         int n=(data[++i]<<8);
360                         n |= (data[++i]);
361                         ++i;
362                         switch(n)
363                         {
364                                 case 12:
365                                         eDebug("unsup. ISO8859-12 enc.");
366                                         break;
367                                 default:
368                                         table=n;
369                                         break;
370                         }
371                         break;
372                 }
373                 case 0x11:
374                         eDebug("unsup. Basic Multilingual Plane of ISO/IEC 10646-1 enc.");
375                         ++i;
376                         break;
377                 case 0x12:
378                         ++i;
379                         eDebug("unsup. KSC 5601 enc.");
380                         break;
381                 case 0x13:
382                         ++i;
383                         eDebug("unsup. GB-2312-1980 enc.");
384                         break;
385                 case 0x14:
386                         ++i;
387                         eDebug("unsup. Big5 subset of ISO/IEC 10646-1 enc.");
388                         break;
389                 case 0x15: // UTF-8 encoding of ISO/IEC 10646-1
390                         return std::string((char*)data+1, len-1);
391                 case 0x0:
392                 case 0xC ... 0xF:
393                 case 0x16 ... 0x1F:
394                         eDebug("reserved %d", data[0]);
395                         ++i;
396                         break;
397         }
398
399         bool useTwoCharMapping =
400                 tsidonid && encodingHandler.getTransponderUseTwoCharMapping(tsidonid);
401
402         unsigned char res[2048];
403         while (i < len)
404         {
405                 unsigned long code=0;
406
407                 if ( useTwoCharMapping && i+1 < len &&
408                         (code=doVideoTexSuppl(data[i], data[i+1])) )
409                         i+=2;
410
411                 if (!code)
412                         code=recode(data[i++], table);
413                 if (!code)
414                         continue;
415                                 // Unicode->UTF8 encoding
416                 if (code < 0x80) // identity ascii <-> utf8 mapping
417                         res[t++]=char(code);
418                 else if (code < 0x800) // two byte mapping
419                 {
420                         res[t++]=(code>>6)|0xC0;
421                         res[t++]=(code&0x3F)|0x80;
422                 } else if (code < 0x10000) // three bytes mapping
423                 {
424                         res[t++]=(code>>12)|0xE0;
425                         res[t++]=((code>>6)&0x3F)|0x80;
426                         res[t++]=(code&0x3F)|0x80;
427                 } else
428                 {
429                         res[t++]=(code>>18)|0xF0;
430                         res[t++]=((code>>12)&0x3F)|0x80;
431                         res[t++]=((code>>6)&0x3F)|0x80;
432                         res[t++]=(code&0x3F)|0x80;
433                 }
434                 if (t+4 > 2047)
435                 {
436                         eDebug("convertDVBUTF8 buffer to small.. break now");
437                         break;
438                 }
439         }
440         return std::string((char*)res, t);
441 }
442
443 std::string convertUTF8DVB(const std::string &string, int table)
444 {
445         unsigned long *coding_table=0;
446
447         int len=string.length(), t=0;
448
449         unsigned char buf[len];
450
451         for(int i=0;i<len;i++)
452         {
453                 unsigned char c1=string[i];
454                 unsigned int c;
455                 if(c1<0x80)
456                         c=c1;
457                 else
458                 {
459                         i++;
460                         unsigned char c2=string[i];
461                         c=((c1&0x3F)<<6) + (c2&0x3F);
462                         if (table==0||table==1||c1<0xA0)
463                                 ;
464                         else
465                         {
466                                 if (!coding_table)
467                                 {
468                                         switch(table)
469                                         {
470                                                 case 2:
471                                                         coding_table = c88592;
472                                                         break;
473                                                 case 3:
474                                                         coding_table = c88593;
475                                                         break;
476                                                 case 4:
477                                                         coding_table = c88594;
478                                                         break;
479                                                 case 5:
480                                                         coding_table = c88595;
481                                                         break;
482                                                 case 6:
483                                                         coding_table = c88596;
484                                                         break;
485                                                 case 7:
486                                                         coding_table = c88597;
487                                                         break;
488                                                 case 8:
489                                                         coding_table = c88598;
490                                                         break;
491                                                 case 9:
492                                                         coding_table = c88599;
493                                                         break;
494                                                 case 10:
495                                                         coding_table = c885910;
496                                                         break;
497                                                 case 11:
498                                                         coding_table = c885911;
499                                                         break;
500 /*                              case 12:   // reserved.. for indian use
501                                                 coding_table = c885912;
502                                                 break;*/
503                                                 case 13:
504                                                         coding_table = c885913;
505                                                         break;
506                                                 case 14:
507                                                         coding_table = c885914;
508                                                         break;
509                                                 case 15:
510                                                         coding_table = c885915;
511                                                         break;
512                                                 case 16:
513                                                         coding_table = c885916;
514                                                         break;
515                                                 default:
516                                                         eFatal("unknown coding table %d", table);
517                                                         break;
518                                         }
519                                 }
520                                 for(unsigned int j=0;j<96;j++)
521                                 {
522                                         if(coding_table[j]==c)
523                                         {
524                                                 c=0xA0+j;
525                                                 break;
526                                         }
527                                 }
528                         }
529                 }
530                 buf[t++]=(unsigned char)c;
531         }
532         return std::string((char*)buf,t);
533 }
534
535 std::string convertLatin1UTF8(const std::string &string)
536 {
537         unsigned int t=0, i=0, len=string.size();
538
539         unsigned char res[2048];
540
541         while (i < len)
542         {
543                 unsigned long code=(unsigned char)string[i++];
544                                 // Unicode->UTF8 encoding
545                 if (code < 0x80) // identity latin <-> utf8 mapping
546                         res[t++]=char(code);
547                 else if (code < 0x800) // two byte mapping
548                 {
549                         res[t++]=(code>>6)|0xC0;
550                         res[t++]=(code&0x3F)|0x80;
551                 } else if (code < 0x10000) // three bytes mapping
552                 {
553                         res[t++]=(code>>12)|0xE0;
554                         res[t++]=((code>>6)&0x3F)|0x80;
555                         res[t++]=(code&0x3F)|0x80;
556                 } else
557                 {
558                         res[t++]=(code>>18)|0xF0;
559                         res[t++]=((code>>12)&0x3F)|0x80;
560                         res[t++]=((code>>6)&0x3F)|0x80;
561                         res[t++]=(code&0x3F)|0x80;
562                 }
563                 if (t+4 > 2047)
564                 {
565                         eDebug("convertLatin1UTF8 buffer to small.. break now");
566                         break;
567                 }
568         }
569         return std::string((char*)res, t);
570 }
571
572 int isUTF8(const std::string &string)
573 {
574         unsigned int len=string.size();
575
576         for (unsigned int i=0; i < len; ++i)
577         {
578                 if (!(string[i]&0x80)) // normal ASCII
579                         continue;
580                 if ((string[i] & 0xE0) == 0xC0) // one char following.
581                 {
582                                 // first, length check:
583                         if (i+1 >= len)
584                                 return 0; // certainly NOT utf-8
585                         i++;
586                         if ((string[i]&0xC0) != 0x80)
587                                 return 0; // no, not UTF-8.
588                 } else if ((string[i] & 0xF0) == 0xE0)
589                 {
590                         if ((i+1) >= len)
591                                 return 0;
592                         i++;
593                         if ((string[i]&0xC0) != 0x80)
594                                 return 0;
595                         i++;
596                         if ((string[i]&0xC0) != 0x80)
597                                 return 0;
598                 }
599         }
600         return 1; // can be UTF8 (or pure ASCII, at least no non-UTF-8 8bit characters)
601 }
602
603 std::string removeDVBChars(const std::string &s)
604 {
605         std::string res;
606         
607         int len = s.length();
608         
609         for(int i = 0; i < len; i++)
610         {
611                 unsigned char c1 = s[i];
612                 unsigned int c;
613                 
614                         /* UTF8? decode (but only simple) */
615                 if((c1 > 0x80) && (i < len-1))
616                 {
617                         unsigned char c2 = s[i + 1];
618                         c = ((c1&0x3F)<<6) + (c2&0x3F);
619                         if ((c >= 0x80) && (c <= 0x9F))
620                         {
621                                 ++i; /* skip 2nd utf8 char */
622                                 continue;
623                         }
624                 }
625                 
626                 res += s[i];
627         }
628         
629         return res;
630 }
631
632 void makeUpper(std::string &s)
633 {
634         std::transform(s.begin(), s.end(), s.begin(), (int(*)(int)) toupper);
635 }
636
637 std::string replace_all(const std::string &in, const std::string &entity, const std::string &symbol)
638 {
639         std::string out = in;
640         std::string::size_type loc = 0;
641         while (( loc = out.find(entity, loc)) != std::string::npos )
642         out.replace(loc, entity.length(), symbol);
643         return out;
644 }