static VALUE
rb_file_s_basename(int argc, VALUE *argv)
{
VALUE fname, fext, basename;
const char *name, *p;
long f, n;
rb_encoding *enc;
if (rb_scan_args(argc, argv, "11", &fname, &fext) == 2) {
rb_encoding *enc;
StringValue(fext);
if (!rb_enc_asciicompat(enc = rb_enc_get(fext))) {
rb_raise(rb_eEncCompatError, "ascii incompatible character encodings: %s",
rb_enc_name(enc));
}
}
FilePathStringValue(fname);
if (!NIL_P(fext)) enc = rb_enc_check(fname, fext);
else enc = rb_enc_get(fname);
if ((n = RSTRING_LEN(fname)) == 0 || !*(name = RSTRING_PTR(fname)))
return rb_str_new_shared(fname);
p = ruby_enc_find_basename(name, &f, &n, enc);
if (n >= 0) {
if (NIL_P(fext)) {
f = n;
}
else {
rb_encoding *fenc = rb_enc_get(fext);
const char *fp;
if (enc != fenc &&
rb_enc_str_coderange(fext) != ENC_CODERANGE_7BIT) {
fext = rb_str_conv_enc(fext, fenc, enc);
}
fp = StringValueCStr(fext);
if (!(f = rmext(p, f, n, fp, RSTRING_LEN(fext), enc))) {
f = n;
}
RB_GC_GUARD(fext);
}
if (f == RSTRING_LEN(fname)) return rb_str_new_shared(fname);
}
basename = rb_str_new(p, f);
rb_enc_copy(basename, fname);
OBJ_INFECT(basename, fname);
return basename;
}