2 * Copyright (C) 2005-2008 Atsushi Konno All rights reserved.
3 * Copyright (C) 2005 QSDN,Inc. All rights reserved.
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
9 * http://www.apache.org/licenses/LICENSE-2.0
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
18 #include "chxj_encoding.h"
19 #include "chxj_apply_convrule.h"
20 #include "chxj_url_encode.h"
23 #if defined(HAVE_LIBICONV_HOOK)
24 # include "iconv_hook/iconv.h"
26 # if defined(HAVE_LIBICONV)
29 # error "Please install libiconv or libiconv_hook. and Please set LD_LIBRARY_PATH."
35 chxj_encoding(request_rec *r, const char* src, apr_size_t* len)
45 mod_chxj_config* dconf;
46 chxjconvrule_entry* entryp;
49 DBG(r,"start chxj_encoding()");
51 dconf = ap_get_module_config(r->per_dir_config, &chxj_module);
54 DBG(r,"none encoding.");
58 entryp = chxj_apply_convrule(r, dconf->convrules);
59 if (entryp->encoding == NULL) {
60 DBG(r,"none encoding.");
64 if (STRCASEEQ('n','N',"none", entryp->encoding)) {
65 DBG(r,"none encoding.");
69 ibuf = apr_palloc(r->pool, ilen+1);
71 DBG(r,"end chxj_encoding()");
74 memset(ibuf, 0, ilen+1);
75 memcpy(ibuf, src, ilen);
78 spos = obuf = apr_palloc(r->pool, olen);
80 DBG(r,"end chxj_encoding()");
83 DBG(r,"encode convert [%s] -> [%s]", entryp->encoding, "CP932");
85 memset(obuf, 0, olen);
86 cd = iconv_open("CP932", entryp->encoding);
87 if (cd == (iconv_t)-1) {
88 if (EINVAL == errno) {
89 ERR(r, "The conversion from %s to %s is not supported by the implementation.", entryp->encoding, "CP932");
92 ERR(r, "iconv open failed. from:[%s] to:[%s] errno:[%d]", entryp->encoding, "CP932", errno);
94 DBG(r,"end chxj_encoding()");
98 result = iconv(cd, &ibuf, &ilen, &obuf, &olen);
99 if (result == (size_t)(-1)) {
100 if (E2BIG == errno) {
101 ERR(r, "There is not sufficient room at *outbuf.");
103 else if (EILSEQ == errno) {
104 ERR(r, "An invalid multibyte sequence has been encountered in the input. input:[%s]", ibuf);
106 else if (EINVAL == errno) {
107 ERR(r, "An incomplete multibyte sequence has been encountered in the input. input:[%s]", ibuf);
115 DBG(r,"end chxj_encoding() len=[%d] obuf=[%.*s]", (int)*len, (int)*len, spos);
121 chxj_rencoding(request_rec *r, const char* src, apr_size_t* len)
131 mod_chxj_config* dconf;
132 chxjconvrule_entry* entryp;
134 DBG(r,"start chxj_rencoding()");
136 dconf = ap_get_module_config(r->per_dir_config, &chxj_module);
138 DBG(r,"none encoding.");
139 DBG(r,"end chxj_rencoding()");
143 entryp = chxj_apply_convrule(r, dconf->convrules);
144 if (! entryp->encoding) {
145 DBG(r,"none encoding.");
146 DBG(r,"end chxj_rencoding()");
150 if (STRCASEEQ('n','N',"none", entryp->encoding)) {
151 DBG(r,"none encoding.");
152 DBG(r,"end chxj_rencoding()");
157 ibuf = apr_palloc(r->pool, ilen+1);
159 DBG(r,"end chxj_rencoding()");
163 memset(ibuf, 0, ilen+1);
164 memcpy(ibuf, src, ilen+0);
167 spos = obuf = apr_palloc(r->pool, olen);
169 DBG(r,"end chxj_rencoding()");
172 DBG(r,"encode convert [%s] -> [%s]", "CP932", entryp->encoding);
174 memset(obuf, 0, olen);
176 cd = iconv_open(entryp->encoding, "CP932");
177 if (cd == (iconv_t)-1) {
178 DBG(r,"end chxj_rencoding()");
183 result = iconv(cd, &ibuf, &ilen, &obuf, &olen);
184 if (result == (size_t)(-1)) {
191 DBG(r,"end chxj_rencoding() len=[%d] obuf=[%.*s]", (int)*len, (int)*len, spos);
198 chxj_encoding_parameter(request_rec* r, const char* value)
212 DBG(r, "start chxj_encoding_parameter()");
214 src = apr_pstrdup(r->pool, value);
216 spos = strchr(src, '?');
218 DBG(r, "end chxj_encoding_parameter()");
223 src_sv = apr_pstrdup(r->pool, src);
224 param = apr_palloc(r->pool, 1);
232 pair = apr_strtok(spos, "&", &pstat);
235 if (strncasecmp(pair, "amp;", 4) == 0) {
239 key = apr_strtok(pair, "=", &vstat);
240 val = apr_strtok(NULL, "=", &vstat);
242 val = chxj_url_decode(r, val);
243 len = (apr_size_t)strlen(val);
244 val = chxj_encoding(r, val, &len);
245 val = chxj_url_encode(r, val);
246 if (strlen(param) == 0) {
247 param = apr_pstrcat(r->pool, param, key, "=", val, NULL);
251 param = apr_pstrcat(r->pool, param, "&", key, "=", val, NULL);
254 param = apr_pstrcat(r->pool, param, "&", key, "=", val, NULL);
259 if (strlen(param) == 0) {
260 param = apr_pstrcat(r->pool, param, key, NULL);
264 param = apr_pstrcat(r->pool, param, "&", key, NULL);
267 param = apr_pstrcat(r->pool, param, "&", key, NULL);
272 DBG(r, "end chxj_encoding_parameter()");
274 return apr_pstrcat(r->pool, src_sv, "?", param, NULL);