* ext/iconv/iconv.c (iconv_failure_initialize): conform with
orthodox initialization method. * ext/iconv/iconv.c (iconv_fail): initialize exception instance from the class, and do not share instance variables with the others. [ruby-dev:21470] git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@4654 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
parent
38d1922038
commit
4d5204c990
@ -1,3 +1,12 @@
|
||||
Thu Oct 2 20:33:49 2003 Nobuyoshi Nakada <nobu@ruby-lang.org>
|
||||
|
||||
* ext/iconv/iconv.c (iconv_failure_initialize): conform with
|
||||
orthodox initialization method.
|
||||
|
||||
* ext/iconv/iconv.c (iconv_fail): initialize exception instance
|
||||
from the class, and do not share instance variables with the
|
||||
others. [ruby-dev:21470]
|
||||
|
||||
Thu Oct 2 18:20:27 2003 Nobuyoshi Nakada <nobu@ruby-lang.org>
|
||||
|
||||
* time.c (Init_Time): define initialize. [ruby-dev:21469]
|
||||
|
@ -50,17 +50,17 @@ struct iconv_env_t
|
||||
int argc;
|
||||
VALUE *argv;
|
||||
VALUE ret;
|
||||
VALUE (*append)_((VALUE, VALUE));
|
||||
};
|
||||
|
||||
static VALUE rb_eIconvFailure;
|
||||
static VALUE rb_eIconvIllegalSeq;
|
||||
static VALUE rb_eIconvInvalidChar;
|
||||
static VALUE rb_eIconvOutOfRange;
|
||||
static ID rb_inserter;
|
||||
|
||||
static ID rb_success, rb_failed, rb_mesg;
|
||||
static VALUE iconv_fail _((VALUE error, VALUE success, VALUE failed, struct iconv_env_t* env));
|
||||
static VALUE iconv_failure_initialize _((VALUE error, VALUE success, VALUE failed, struct iconv_env_t* env));
|
||||
static ID rb_success, rb_failed;
|
||||
static VALUE iconv_fail _((VALUE error, VALUE success, VALUE failed, struct iconv_env_t* env, const char *mesg));
|
||||
static VALUE iconv_failure_initialize _((VALUE error, VALUE mesg, VALUE success, VALUE failed));
|
||||
static VALUE iconv_failure_success _((VALUE self));
|
||||
static VALUE iconv_failure_failed _((VALUE self));
|
||||
|
||||
@ -223,16 +223,16 @@ iconv_try
|
||||
/* try the left in next loop */
|
||||
break;
|
||||
case EILSEQ:
|
||||
return rb_class_new_instance(0, 0, rb_eIconvIllegalSeq);
|
||||
return rb_eIconvIllegalSeq;
|
||||
case EINVAL:
|
||||
return rb_class_new_instance(0, 0, rb_eIconvInvalidChar);
|
||||
return rb_eIconvInvalidChar;
|
||||
default:
|
||||
rb_sys_fail("iconv");
|
||||
}
|
||||
}
|
||||
else if (*inlen > 0) {
|
||||
/* something goes wrong */
|
||||
return rb_class_new_instance(0, 0, rb_eIconvIllegalSeq);
|
||||
return rb_eIconvIllegalSeq;
|
||||
}
|
||||
else if (ret) {
|
||||
return Qnil; /* conversion */
|
||||
@ -242,35 +242,15 @@ iconv_try
|
||||
|
||||
#define FAILED_MAXLEN 16
|
||||
|
||||
static VALUE
|
||||
iconv_failure_initialize
|
||||
static VALUE iconv_failure_initialize
|
||||
#ifdef HAVE_PROTOTYPES
|
||||
(VALUE error, VALUE success, VALUE failed, struct iconv_env_t* env)
|
||||
(VALUE error, VALUE mesg, VALUE success, VALUE failed)
|
||||
#else /* HAVE_PROTOTYPES */
|
||||
(error, success, failed, env)
|
||||
VALUE error;
|
||||
VALUE success;
|
||||
VALUE failed;
|
||||
struct iconv_env_t *env;
|
||||
(error, mesg, success, failed)
|
||||
VALUE error, mesg, success, failed;
|
||||
#endif /* HAVE_PROTOTYPES */
|
||||
{
|
||||
if (NIL_P(rb_attr_get(error, rb_mesg))) {
|
||||
if (TYPE(failed) != T_STRING || RSTRING(failed)->len < FAILED_MAXLEN) {
|
||||
rb_ivar_set(error, rb_mesg, rb_inspect(failed));
|
||||
}
|
||||
else {
|
||||
VALUE mesg = rb_inspect(rb_str_substr(failed, 0, FAILED_MAXLEN));
|
||||
rb_str_cat2(mesg, "...");
|
||||
rb_ivar_set(error, rb_mesg, mesg);
|
||||
}
|
||||
}
|
||||
if (env) {
|
||||
success = rb_funcall3(env->ret, rb_inserter, 1, &success);
|
||||
if (env->argc > 0) {
|
||||
*(env->argv) = failed;
|
||||
failed = rb_ary_new4(env->argc, env->argv);
|
||||
}
|
||||
}
|
||||
rb_call_super(1, &mesg);
|
||||
rb_ivar_set(error, rb_success, success);
|
||||
rb_ivar_set(error, rb_failed, failed);
|
||||
return error;
|
||||
@ -279,14 +259,36 @@ iconv_failure_initialize
|
||||
static VALUE
|
||||
iconv_fail
|
||||
#ifdef HAVE_PROTOTYPES
|
||||
(VALUE error, VALUE success, VALUE failed, struct iconv_env_t* env)
|
||||
(VALUE error, VALUE success, VALUE failed, struct iconv_env_t* env, const char *mesg)
|
||||
#else /* HAVE_PROTOTYPES */
|
||||
(error, success, failed, env)
|
||||
(error, success, failed, env, mesg)
|
||||
VALUE error, success, failed;
|
||||
struct iconv_env_t *env;
|
||||
const char *mesg;
|
||||
#endif /* HAVE_PROTOTYPES */
|
||||
{
|
||||
error = iconv_failure_initialize(error, success, failed, env);
|
||||
VALUE args[3];
|
||||
|
||||
if (mesg && *mesg) {
|
||||
args[0] = rb_str_new2(mesg);
|
||||
}
|
||||
else if (TYPE(failed) != T_STRING || RSTRING(failed)->len < FAILED_MAXLEN) {
|
||||
args[0] = rb_inspect(failed);
|
||||
}
|
||||
else {
|
||||
args[0] = rb_inspect(rb_str_substr(failed, 0, FAILED_MAXLEN));
|
||||
rb_str_cat2(args[0], "...");
|
||||
}
|
||||
args[1] = success;
|
||||
args[2] = failed;
|
||||
if (env) {
|
||||
args[1] = env->append(rb_obj_dup(env->ret), success);
|
||||
if (env->argc > 0) {
|
||||
*(env->argv) = failed;
|
||||
args[2] = rb_ary_new4(env->argc, env->argv);
|
||||
}
|
||||
}
|
||||
error = rb_class_new_instance(3, args, error);
|
||||
if (!rb_block_given_p()) rb_exc_raise(error);
|
||||
ruby_errinfo = error;
|
||||
return rb_yield(failed);
|
||||
@ -352,7 +354,7 @@ iconv_convert
|
||||
error = iconv_try(cd, &inptr, &inlen, &outptr, &outlen);
|
||||
if (RTEST(error)) {
|
||||
unsigned int i;
|
||||
rescue = iconv_fail(error, Qnil, Qnil, env);
|
||||
rescue = iconv_fail(error, Qnil, Qnil, env, 0);
|
||||
if (TYPE(rescue) == T_ARRAY) {
|
||||
str = RARRAY(rescue)->len > 0 ? RARRAY(rescue)->ptr[0] : Qnil;
|
||||
}
|
||||
@ -388,10 +390,12 @@ iconv_convert
|
||||
inlen = length;
|
||||
|
||||
do {
|
||||
char errmsg[50];
|
||||
const char *tmpstart = inptr;
|
||||
outptr = buffer;
|
||||
outlen = sizeof(buffer);
|
||||
|
||||
errmsg[0] = 0;
|
||||
error = iconv_try(cd, &inptr, &inlen, &outptr, &outlen);
|
||||
|
||||
if (0 <= outlen && outlen <= sizeof(buffer)) {
|
||||
@ -422,9 +426,8 @@ iconv_convert
|
||||
}
|
||||
else {
|
||||
/* Some iconv() have a bug, return *outlen out of range */
|
||||
char errmsg[50];
|
||||
sprintf(errmsg, "bug?(output length = %d)", sizeof(buffer) - outlen);
|
||||
error = rb_exc_new2(rb_eIconvOutOfRange, errmsg);
|
||||
error = rb_eIconvOutOfRange;
|
||||
}
|
||||
|
||||
if (RTEST(error)) {
|
||||
@ -432,8 +435,10 @@ iconv_convert
|
||||
|
||||
if (!ret)
|
||||
ret = rb_str_derive(str, instart, inptr - instart);
|
||||
else if (inptr > instart)
|
||||
rb_str_cat(ret, instart, inptr - instart);
|
||||
str = rb_str_derive(str, inptr, inlen);
|
||||
rescue = iconv_fail(error, ret, str, env);
|
||||
rescue = iconv_fail(error, ret, str, env, errmsg);
|
||||
if (TYPE(rescue) == T_ARRAY) {
|
||||
if ((len = RARRAY(rescue)->len) > 0)
|
||||
rb_str_concat(ret, RARRAY(rescue)->ptr[0]);
|
||||
@ -568,13 +573,13 @@ iconv_s_convert
|
||||
|
||||
for (; env->argc > 0; --env->argc, ++env->argv) {
|
||||
VALUE s = iconv_convert(env->cd, last = *(env->argv), 0, -1, env);
|
||||
rb_funcall3(env->ret, rb_inserter, 1, &s);
|
||||
env->append(env->ret, s);
|
||||
}
|
||||
|
||||
if (!NIL_P(last)) {
|
||||
VALUE s = iconv_convert(env->cd, Qnil, 0, 0, env);
|
||||
if (RSTRING(s)->len)
|
||||
rb_funcall3(env->ret, rb_inserter, 1, &s);
|
||||
env->append(env->ret, s);
|
||||
}
|
||||
|
||||
return env->ret;
|
||||
@ -598,6 +603,7 @@ iconv_s_iconv
|
||||
|
||||
arg.argc = argc -= 2;
|
||||
arg.argv = argv + 2;
|
||||
arg.append = rb_ary_push;
|
||||
arg.ret = rb_ary_new2(argc);
|
||||
arg.cd = iconv_create(argv[0], argv[1]);
|
||||
return rb_ensure(iconv_s_convert, (VALUE)&arg, iconv_free, ICONV2VALUE(arg.cd));
|
||||
@ -616,6 +622,7 @@ iconv_s_conv
|
||||
|
||||
arg.argc = 1;
|
||||
arg.argv = &str;
|
||||
arg.append = rb_str_append;
|
||||
arg.ret = rb_str_new(0, 0);
|
||||
arg.cd = iconv_create(to, from);
|
||||
return rb_ensure(iconv_s_convert, (VALUE)&arg, iconv_free, ICONV2VALUE(arg.cd));
|
||||
@ -840,6 +847,7 @@ Init_iconv _((void))
|
||||
rb_define_method(rb_cIconv, "iconv", iconv_iconv, -1);
|
||||
|
||||
rb_eIconvFailure = rb_define_module_under(rb_cIconv, "Failure");
|
||||
rb_define_method(rb_eIconvFailure, "initialize", iconv_failure_initialize, 3);
|
||||
rb_define_method(rb_eIconvFailure, "success", iconv_failure_success, 0);
|
||||
rb_define_method(rb_eIconvFailure, "failed", iconv_failure_failed, 0);
|
||||
rb_define_method(rb_eIconvFailure, "inspect", iconv_failure_inspect, 0);
|
||||
@ -851,10 +859,8 @@ Init_iconv _((void))
|
||||
rb_include_module(rb_eIconvInvalidChar, rb_eIconvFailure);
|
||||
rb_include_module(rb_eIconvOutOfRange, rb_eIconvFailure);
|
||||
|
||||
rb_inserter = rb_intern("<<");
|
||||
rb_success = rb_intern("success");
|
||||
rb_failed = rb_intern("failed");
|
||||
rb_mesg = rb_intern("mesg");
|
||||
|
||||
charset_map = rb_hash_new();
|
||||
rb_gc_register_address(&charset_map);
|
||||
|
Loading…
x
Reference in New Issue
Block a user