Beispiel #1
0
VALUE
rpm_db_transaction(int argc, VALUE* argv, VALUE db)
{
	VALUE trans;
	rpm_trans_t* ts;
	const char* root = "/";

#if 0
	if (OBJ_FROZEN(db)) {
		rb_error_frozen("RPM::DB");
	}
#endif
	switch (argc) {
	case 0:
		break;

	case 1:
		if (TYPE(argv[0]) != T_STRING) {
			rb_raise(rb_eTypeError, "illegal argument type");
		}
		root = RSTRING_PTR(argv[0]);
		break;

	default:
		rb_raise(rb_eArgError, "argument too many(0..1)");
	}

	ts = ALLOC(rpm_trans_t);
#if RPM_VERSION_CODE < RPM_VERSION(4,1,0)
	ts->ts = rpmtransCreateSet(RPM_DB(db), root);
#else
	ts->ts = rpmtsCreate();
	rpmtsSetRootDir(ts->ts, root);
#endif
	ts->script_fd = 0;
	ts->db = DATA_PTR(db);
	trans = Data_Wrap_Struct(rpm_cTransaction, NULL, transaction_free, ts);
	db_ref(ts->db);
	rb_ivar_set(trans, id_db, db);

	rb_catch("abort", transaction_yield, trans);

	if (rb_ivar_get(trans, id_aborted) == Qtrue) {
		return Qfalse;
	} else if (rb_ivar_get(trans, id_commited) != Qtrue && !OBJ_FROZEN(db)) {
		rb_catch("abort", transaction_commit, trans);
	}

	return rb_ivar_get(trans, id_pl);
}
Beispiel #2
0
static void
rb_struct_modify(VALUE s)
{
    if (OBJ_FROZEN(s)) rb_error_frozen("Struct");
    if (!OBJ_TAINTED(s) && rb_safe_level() >= 4)
       rb_raise(rb_eSecurityError, "Insecure: can't modify Struct");
}
Beispiel #3
0
VALUE
rb_singleton_class(VALUE obj)
{
    VALUE klass;

    if (FIXNUM_P(obj) || SYMBOL_P(obj)) {
	rb_raise(rb_eTypeError, "can't define singleton");
    }
    if (rb_special_const_p(obj)) {
	SPECIAL_SINGLETON(Qnil, rb_cNilClass);
	SPECIAL_SINGLETON(Qfalse, rb_cFalseClass);
	SPECIAL_SINGLETON(Qtrue, rb_cTrueClass);
	rb_bug("unknown immediate %ld", obj);
    }

    DEFER_INTS;
    if (FL_TEST(RBASIC(obj)->klass, FL_SINGLETON) &&
	rb_iv_get(RBASIC(obj)->klass, "__attached__") == obj) {
	klass = RBASIC(obj)->klass;
    }
    else {
	klass = rb_make_metaclass(obj, RBASIC(obj)->klass);
    }
    if (OBJ_TAINTED(obj)) {
	OBJ_TAINT(klass);
    }
    else {
	FL_UNSET(klass, FL_TAINT);
    }
    if (OBJ_FROZEN(obj)) OBJ_FREEZE(klass);
    ALLOW_INTS;

    return klass;
}
Beispiel #4
0
VALUE
rb_singleton_class(VALUE obj)
{
    if (FIXNUM_P(obj) || SYMBOL_P(obj) || FIXFLOAT_P(obj)) {
	rb_raise(rb_eTypeError, "can't define singleton");
    }
    if (rb_special_const_p(obj)) {
	SPECIAL_SINGLETON(Qnil, rb_cNilClass);
	SPECIAL_SINGLETON(Qfalse, rb_cFalseClass);
	SPECIAL_SINGLETON(Qtrue, rb_cTrueClass);
	rb_bug("unknown immediate %ld", obj);
    }

    VALUE klass;
    switch (TYPE(obj)) {
	case T_CLASS:
	case T_MODULE:
	    // FIXME we should really create a new metaclass here.
	    klass = *(VALUE *)obj;
	    break;

	default:
	    klass = rb_make_metaclass(obj, RBASIC(obj)->klass);
	    break;
    }

    OBJ_INFECT(klass, obj);
    if (OBJ_FROZEN(obj)) {
	OBJ_FREEZE(klass);
    }

    return klass;
}
Beispiel #5
0
char *
na_get_pointer_for_write(VALUE self)
{
    char *ptr;
    narray_t *na;
    GetNArray(self,na);

    if (OBJ_FROZEN(self)) {
        rb_raise(rb_eRuntimeError, "cannot write to frozen NArray.");
    }

    if (NA_TYPE(na) == NARRAY_DATA_T) {
        ptr = NA_DATA_PTR(na);
        if (na->size > 0 && ptr == NULL) {
            rb_funcall(self, id_allocate, 0);
            ptr = NA_DATA_PTR(na);
        }
    } else {
        ptr = na_get_pointer(self);
        if (NA_SIZE(na) > 0 && ptr == NULL) {
            rb_raise(rb_eRuntimeError,"cannot write to unallocated NArray");
        }
    }

    //NA_SET_LOCK(na);

    return ptr;
}
static void
remove_method(VALUE klass, ID mid)
{
    st_data_t data;
    rb_method_entry_t *me = 0;

    if (klass == rb_cObject) {
	rb_secure(4);
    }
    if (rb_safe_level() >= 4 && !OBJ_UNTRUSTED(klass)) {
	rb_raise(rb_eSecurityError, "Insecure: can't remove method");
    }
    if (OBJ_FROZEN(klass))
	rb_error_frozen("class/module");
    if (mid == object_id || mid == id__send__ || mid == idInitialize) {
	rb_warn("removing `%s' may cause serious problems", rb_id2name(mid));
    }

    if (!st_lookup(RCLASS_M_TBL(klass), mid, &data) ||
	!(me = (rb_method_entry_t *)data) ||
	(!me->def || me->def->type == VM_METHOD_TYPE_UNDEF)) {
	rb_name_error(mid, "method `%s' not defined in %s",
		      rb_id2name(mid), rb_class2name(klass));
    }
    st_delete(RCLASS_M_TBL(klass), &mid, &data);

    rb_vm_check_redefinition_opt_method(me);
    rb_clear_cache_for_undef(klass, mid);
    rb_free_method_entry(me);

    CALL_METHOD_HOOK(klass, removed, mid);
}
Beispiel #7
0
static VALUE
rb_set_clone(VALUE rcv)
{
    VALUE clone = rb_set_dup(rcv);
    if (OBJ_FROZEN(rcv))
	OBJ_FREEZE(clone);
    return clone;
}
Beispiel #8
0
static void
rb_provide_feature(VALUE feature)
{
    if (OBJ_FROZEN(get_loaded_features())) {
	rb_raise(rb_eRuntimeError,
		 "$LOADED_FEATURES is frozen; cannot append feature");
    }
    rb_ary_push(get_loaded_features(), feature);
}
Beispiel #9
0
static VALUE
rb_set_clone(VALUE rcv, SEL sel)
{
    VALUE clone = rb_set_dup(rcv, 0);
    if (OBJ_FROZEN(rcv)) {
	OBJ_FREEZE(clone);
    }
    return clone;
}
Beispiel #10
0
VALUE
rhash_aset(VALUE hash, SEL sel, VALUE key, VALUE val)
{
    rhash_modify(hash);
    if (TYPE(key) == T_STRING && !OBJ_FROZEN(key)) {
        key = rb_str_dup(key);
        OBJ_FREEZE(key);
    }
    st_insert(RHASH(hash)->tbl, key, val);
    return val;
}
Beispiel #11
0
static VALUE
rg_match_all(gint argc, VALUE *argv, VALUE self)
{
    VALUE rb_string, rb_start_position, rb_match_options, rb_options;
    VALUE rb_frozen_string, rb_match_info;
    GMatchInfo *match_info = NULL;
    GError *error = NULL;
    const gchar *string;
    gssize string_len = -1;
    gint start_position = 0;
    GRegexMatchFlags match_options = 0;

    rb_scan_args(argc, argv, "11", &rb_string, &rb_options);

    rbg_scan_options(rb_options,
                     "start_position", &rb_start_position,
                     "match_options", &rb_match_options,
                     NULL);

    if (OBJ_FROZEN(rb_string)) {
        rb_frozen_string = rb_string;
    } else {
        rb_frozen_string = rb_str_dup(rb_string);
        rb_str_freeze(rb_frozen_string);
    }

    string = RVAL2CSTR(rb_frozen_string);
    string_len = RSTRING_LEN(rb_frozen_string);


    if (!NIL_P(rb_start_position))
        start_position = NUM2INT(rb_start_position);
    if (!NIL_P(rb_match_options))
        match_options = RVAL2GREGEXMATCHOPTIONSFLAGS(rb_match_options);

    g_regex_match_all_full(_SELF(self),
                           string,
                           string_len,
                           start_position,
                           match_options,
                           &match_info,
                           &error);

    if (error)
        RAISE_GERROR(error);

    if (!match_info)
        return Qnil;

    rb_match_info = GMATCHINFO2RVAL(match_info);
    g_match_info_unref(match_info);
    rb_iv_set(rb_match_info, "@string", rb_frozen_string);
    return rb_match_info;
}
Beispiel #12
0
/*
    Method:     Draw#clone
    Notes:      see dup, init_copy
*/
VALUE
Draw_clone(VALUE self)
{
    volatile VALUE clone;

    clone = Draw_dup(self);
    if (OBJ_FROZEN(self))
    {
        OBJ_FREEZE(clone);
    }

    return clone;
}
Beispiel #13
0
/**
 * Clones this object.
 *
 * Ruby usage:
 *   - @verbatim Draw#clone @endverbatim
 *
 * @param self this object
 * @return the clone
 * @see Draw_dup
 * @see Draw_init_copy
 */
VALUE
Draw_clone(VALUE self)
{
    VALUE clone;

    clone = Draw_dup(self);
    if (OBJ_FROZEN(self))
    {
        OBJ_FREEZE(clone);
    }

    RB_GC_GUARD(clone);

    return clone;
}
Beispiel #14
0
static VALUE
thgroup_add_m(VALUE group, VALUE thread, bool check_enclose)
{
    if (OBJ_FROZEN(group)) {
	rb_raise(rb_eThreadError, "can't move to the frozen thread group");
    }

    rb_vm_thread_t *t = GetThreadPtr(thread);

    rb_thread_group_t *new_tg = GetThreadGroupPtr(group);
    if (new_tg->enclosed && check_enclose) {
	rb_raise(rb_eThreadError, "can't move from the enclosed thread group");
    }

    if (t->group != Qnil) {
	if (OBJ_FROZEN(t->group)) {
	    rb_raise(rb_eThreadError,
		    "can't move from the frozen thread group");
	}
	rb_thread_group_t *old_tg = GetThreadGroupPtr(t->group);
	if (old_tg->enclosed && check_enclose) {
	    rb_raise(rb_eThreadError,
		    "can't move from the enclosed thread group");
	}
 	thgroup_lock(old_tg);
	rb_ary_delete(old_tg->threads, thread); 
 	thgroup_unlock(old_tg);
    }

    thgroup_lock(new_tg);
    rb_ary_push(new_tg->threads, thread);
    thgroup_unlock(new_tg);
    GC_WB(&t->group, group);

    return group;
}
Beispiel #15
0
static void
rb_provide_feature(VALUE feature)
{
    VALUE features;

    features = get_loaded_features();
    if (OBJ_FROZEN(features)) {
	rb_raise(rb_eRuntimeError,
		 "$LOADED_FEATURES is frozen; cannot append feature");
    }
    rb_str_freeze(feature);

    rb_ary_push(features, rb_fstring(feature));
    features_index_add(feature, INT2FIX(RARRAY_LEN(features)-1));
    reset_loaded_features_snapshot();
}
Beispiel #16
0
static void
remove_method(VALUE klass, ID mid)
{
    if (klass == rb_cObject) {
	rb_secure(4);
    }
    if (rb_safe_level() >= 4 && !OBJ_TAINTED(klass)) {
	rb_raise(rb_eSecurityError, "Insecure: can't remove method");
    }
    if (OBJ_FROZEN(klass))
	rb_error_frozen("class/module");
    if (mid == object_id || mid == __send__ || mid == idInitialize) {
	rb_warn("removing `%s' may cause serious problem", rb_id2name(mid));
    }
    SEL sel;
    Method m;

    sel = sel_registerName(rb_id2name(mid));
    m = class_getInstanceMethod((Class)klass, sel);
    if (m == NULL) {
	char buf[100];
	size_t len = strlen((char *)sel);
	if (((char *)sel)[len - 1] != ':') {
	    snprintf(buf, sizeof buf, "%s:", (char *)sel);
	    sel = sel_registerName(buf);
	    m = class_getInstanceMethod((Class)klass, sel);
	}
    }
    if (m == NULL) {
	rb_name_error(mid, "method `%s' not defined in %s",
		      rb_id2name(mid), rb_class2name(klass));
    }
    if (rb_vm_get_method_node(method_getImplementation(m)) == NULL) {
	rb_warn("removing pure Objective-C method `%s' may cause serious " \
		"problem", rb_id2name(mid));
    }
    method_setImplementation(m, NULL);

    if (RCLASS_SINGLETON(klass)) {
	rb_funcall(rb_iv_get(klass, "__attached__"), singleton_removed, 1,
		   ID2SYM(mid));
    }
    else {
	rb_funcall(klass, removed, 1, ID2SYM(mid));
    }
}
Beispiel #17
0
VALUE
rb_singleton_class(VALUE obj)
{
    VALUE klass;
    ID attached;

    if (FIXNUM_P(obj) || SYMBOL_P(obj)) {
	rb_raise(rb_eTypeError, "can't define singleton");
    }
    if (rb_special_const_p(obj)) {
	SPECIAL_SINGLETON(Qnil, rb_cNilClass);
	SPECIAL_SINGLETON(Qfalse, rb_cFalseClass);
	SPECIAL_SINGLETON(Qtrue, rb_cTrueClass);
	rb_bug("unknown immediate %ld", obj);
    }

    CONST_ID(attached, "__attached__");
    if (FL_TEST(RBASIC(obj)->klass, FL_SINGLETON) &&
	rb_ivar_get(RBASIC(obj)->klass, attached) == obj) {
	klass = RBASIC(obj)->klass;
    }
    else {
	klass = rb_make_metaclass(obj, RBASIC(obj)->klass);
    }

    if (BUILTIN_TYPE(obj) == T_CLASS) {
	if (rb_iv_get(RBASIC(klass)->klass, "__attached__") != klass)
	    make_metametaclass(klass);
    }
    if (OBJ_TAINTED(obj)) {
	OBJ_TAINT(klass);
    }
    else {
	FL_UNSET(klass, FL_TAINT);
    }
    if (OBJ_UNTRUSTED(obj)) {
	OBJ_UNTRUST(klass);
    }
    else {
	FL_UNSET(klass, FL_UNTRUSTED);
    }
    if (OBJ_FROZEN(obj)) OBJ_FREEZE(klass);

    return klass;
}
Beispiel #18
0
static void
remove_method(VALUE klass, ID mid)
{
    if (klass == rb_cObject) {
	rb_secure(4);
    }
    if (rb_safe_level() >= 4 && !OBJ_UNTRUSTED(klass)) {
	rb_raise(rb_eSecurityError, "Insecure: can't remove method");
    }
    if (OBJ_FROZEN(klass)) {
	rb_error_frozen("class/module");
    }
    if (mid == object_id || mid == __send__ || mid == idInitialize) {
	rb_warn("removing `%s' may cause serious problem", rb_id2name(mid));
    }

    rb_vm_remove_method((Class)klass, mid);
}
Beispiel #19
0
static VALUE
rb_obj_extend(VALUE obj, SEL sel, int argc, VALUE *argv)
{
    if (OBJ_FROZEN(obj)) {
	rb_raise(rb_eRuntimeError, "cannot extend a frozen object");
    }
    if (argc == 0) {
	rb_raise(rb_eArgError, "wrong number of arguments (0 for 1)");
    }
    for (int i = 0; i < argc; i++) {
	Check_Type(argv[i], T_MODULE);
    }
    while (argc--) {
	rb_funcall(argv[argc], rb_intern("extend_object"), 1, obj);
	rb_funcall(argv[argc], rb_intern("extended"), 1, obj);
    }
    return obj;
}
Beispiel #20
0
static void
remove_method(VALUE klass, ID mid)
{
    st_data_t data;
    NODE *body = 0;

    if (klass == rb_cObject) {
	rb_secure(4);
    }
    if (rb_safe_level() >= 4 && !OBJ_TAINTED(klass)) {
	rb_raise(rb_eSecurityError, "Insecure: can't remove method");
    }
    if (OBJ_FROZEN(klass))
	rb_error_frozen("class/module");
    if (mid == object_id || mid == __send__ || mid == idInitialize) {
	rb_warn("removing `%s' may cause serious problem", rb_id2name(mid));
    }
    if (st_lookup(RCLASS_M_TBL(klass), mid, &data)) {
	body = (NODE *)data;
	if (!body || !body->nd_body) body = 0;
	else {
	    st_delete(RCLASS_M_TBL(klass), &mid, &data);
	}
    }
    if (!body) {
	rb_name_error(mid, "method `%s' not defined in %s",
		      rb_id2name(mid), rb_class2name(klass));
    }

    if (nd_type(body->nd_body->nd_body) == NODE_CFUNC) {
	rb_vm_check_redefinition_opt_method(body);
    }

    rb_clear_cache_for_undef(klass, mid);
    if (FL_TEST(klass, FL_SINGLETON)) {
	rb_funcall(rb_iv_get(klass, "__attached__"), singleton_removed, 1,
		   ID2SYM(mid));
    }
    else {
	rb_funcall(klass, removed, 1, ID2SYM(mid));
    }
}
Beispiel #21
0
VALUE
rb_ca_mask_array (VALUE self)
{
  VALUE obj;
  CArray *ca;
  Data_Get_Struct(self, CArray, ca);

  ca_update_mask(ca);
  if ( ca->mask ) {
    obj = Data_Wrap_Struct(ca_class[ca->mask->obj_type],
            ca_mark, ca_free_nop, ca->mask);
    rb_ivar_set(obj, rb_intern("masked_array"), self);
    if ( OBJ_FROZEN(self) ) {
      rb_ca_freeze(obj);
    }
    return obj;
  }
  else {
    return INT2NUM(0);
  }
}
Beispiel #22
0
void
rb_frozen_class_p(VALUE klass)
{
    const char *desc = "something(?!)";

    if (OBJ_FROZEN(klass)) {
	if (RCLASS_SINGLETON(klass))
	    desc = "object";
	else {
	    switch (TYPE(klass)) {
	      case T_MODULE:
	      case T_ICLASS:
		desc = "module";
		break;
	      case T_CLASS:
		desc = "class";
		break;
	    }
	}
	rb_error_frozen(desc);
    }
}
Beispiel #23
0
static void
vm_define_method(rb_thread_t *th, VALUE obj, ID id, VALUE iseqval,
		 rb_num_t is_singleton, NODE *cref)
{
    VALUE klass = cref->nd_clss;
    int noex = (int)cref->nd_visi;
    rb_iseq_t *miseq;
    GetISeqPtr(iseqval, miseq);

    if (NIL_P(klass)) {
	rb_raise(rb_eTypeError, "no class/module to add method");
    }

    if (is_singleton) {
	if (FIXNUM_P(obj) || SYMBOL_P(obj)) {
	    rb_raise(rb_eTypeError,
		     "can't define singleton method \"%s\" for %s",
		     rb_id2name(id), rb_obj_classname(obj));
	}

	if (OBJ_FROZEN(obj)) {
	    rb_error_frozen("object");
	}

	klass = rb_singleton_class(obj);
	noex = NOEX_PUBLIC;
    }

    /* dup */
    COPY_CREF(miseq->cref_stack, cref);
    miseq->klass = klass;
    miseq->defined_method_id = id;
    rb_add_method(klass, id, VM_METHOD_TYPE_ISEQ, miseq, noex);

    if (!is_singleton && noex == NOEX_MODFUNC) {
	rb_add_method(rb_singleton_class(klass), id, VM_METHOD_TYPE_ISEQ, miseq, NOEX_PUBLIC);
    }
    INC_VM_STATE_VERSION();
}
Beispiel #24
0
/*!
 * \internal
 * Returns the singleton class of \a obj. Creates it if necessary.
 *
 * \note DO NOT expose the returned singleton class to
 *       outside of class.c.
 *       Use \ref rb_singleton_class instead for
 *       consistency of the metaclass hierarchy.
 */
static VALUE
singleton_class_of(VALUE obj)
{
    VALUE klass;

    if (FIXNUM_P(obj) || FLONUM_P(obj) || SYMBOL_P(obj)) {
	rb_raise(rb_eTypeError, "can't define singleton");
    }
    if (SPECIAL_CONST_P(obj)) {
	klass = special_singleton_class_of(obj);
	if (NIL_P(klass))
	    rb_bug("unknown immediate %p", (void *)obj);
	return klass;
    }
    else {
	enum ruby_value_type type = BUILTIN_TYPE(obj);
	if (type == T_FLOAT || type == T_BIGNUM) {
	    rb_raise(rb_eTypeError, "can't define singleton");
	}
    }

    if (FL_TEST(RBASIC(obj)->klass, FL_SINGLETON) &&
	rb_ivar_get(RBASIC(obj)->klass, id_attached) == obj) {
	klass = RBASIC(obj)->klass;
    }
    else {
	klass = rb_make_metaclass(obj, RBASIC(obj)->klass);
    }

    if (OBJ_TAINTED(obj)) {
	OBJ_TAINT(klass);
    }
    else {
	FL_UNSET(klass, FL_TAINT);
    }
    if (OBJ_FROZEN(obj)) OBJ_FREEZE(klass);

    return klass;
}
Beispiel #25
0
/*!
 * \internal
 * Returns the singleton class of \a obj. Creates it if necessary.
 *
 * \note DO NOT expose the returned singleton class to
 *       outside of class.c.
 *       Use \ref rb_singleton_class instead for
 *       consistency of the metaclass hierarchy.
 */
static VALUE
singleton_class_of(VALUE obj)
{
    VALUE klass;

    if (FIXNUM_P(obj) || SYMBOL_P(obj)) {
	rb_raise(rb_eTypeError, "can't define singleton");
    }
    if (rb_special_const_p(obj)) {
	SPECIAL_SINGLETON(Qnil, rb_cNilClass);
	SPECIAL_SINGLETON(Qfalse, rb_cFalseClass);
	SPECIAL_SINGLETON(Qtrue, rb_cTrueClass);
	rb_bug("unknown immediate %p", (void *)obj);
    }

    if (FL_TEST(RBASIC(obj)->klass, FL_SINGLETON) &&
	rb_ivar_get(RBASIC(obj)->klass, id_attached) == obj) {
	klass = RBASIC(obj)->klass;
    }
    else {
	klass = rb_make_metaclass(obj, RBASIC(obj)->klass);
    }

    if (OBJ_TAINTED(obj)) {
	OBJ_TAINT(klass);
    }
    else {
	FL_UNSET(klass, FL_TAINT);
    }
    if (OBJ_UNTRUSTED(obj)) {
	OBJ_UNTRUST(klass);
    }
    else {
	FL_UNSET(klass, FL_UNTRUSTED);
    }
    if (OBJ_FROZEN(obj)) OBJ_FREEZE(klass);

    return klass;
}
Beispiel #26
0
/*RHO static*/ VALUE
eval_string_with_cref(VALUE self, VALUE src, VALUE scope, NODE *cref, const char *file, int line)
{
    int state;
    VALUE result = Qundef;
    VALUE envval;
    rb_binding_t *bind = 0;
    rb_thread_t *th = GET_THREAD();
    rb_env_t *env = NULL;
    rb_block_t block;
    volatile int parse_in_eval;
    volatile int mild_compile_error;

    if (file == 0) {
	file = rb_sourcefile();
	line = rb_sourceline();
    }

    parse_in_eval = th->parse_in_eval;
    mild_compile_error = th->mild_compile_error;
    PUSH_TAG();
    if ((state = EXEC_TAG()) == 0) {
	rb_iseq_t *iseq;
	volatile VALUE iseqval;

	if (scope != Qnil) {
	    if (rb_obj_is_kind_of(scope, rb_cBinding)) {
		GetBindingPtr(scope, bind);
		envval = bind->env;
	    }
	    else {
		rb_raise(rb_eTypeError,
			 "wrong argument type %s (expected Binding)",
			 rb_obj_classname(scope));
	    }
	    GetEnvPtr(envval, env);
	    th->base_block = &env->block;
	}
	else {
	    rb_control_frame_t *cfp = rb_vm_get_ruby_level_next_cfp(th, th->cfp);

	    if (cfp != 0) {
		block = *RUBY_VM_GET_BLOCK_PTR_IN_CFP(cfp);
		th->base_block = &block;
		th->base_block->self = self;
		th->base_block->iseq = cfp->iseq;	/* TODO */
	    }
	    else {
		rb_raise(rb_eRuntimeError, "Can't eval on top of Fiber or Thread");
	    }
	}

    //RHO
    if ( TYPE(src) != T_STRING ){
        iseqval = src;
    }else
    //RHO
    {
	    /* make eval iseq */
	    th->parse_in_eval++;
	    th->mild_compile_error++;
	    iseqval = rb_iseq_compile(src, rb_str_new2(file), INT2FIX(line));
	    th->mild_compile_error--;
	    th->parse_in_eval--;
    }

	vm_set_eval_stack(th, iseqval, cref);
	th->base_block = 0;

	if (0) {		/* for debug */
	    printf("%s\n", RSTRING_PTR(rb_iseq_disasm(iseqval)));
	}

	/* save new env */
	GetISeqPtr(iseqval, iseq);
	if (bind && iseq->local_size > 0) {
	    bind->env = rb_vm_make_env_object(th, th->cfp);
	}

	/* kick */
	CHECK_STACK_OVERFLOW(th->cfp, iseq->stack_max);
	result = vm_exec(th);
    }
    POP_TAG();
    th->mild_compile_error = mild_compile_error;
    th->parse_in_eval = parse_in_eval;

    if (state) {
	if (state == TAG_RAISE) {
	    VALUE errinfo = th->errinfo;
	    if (strcmp(file, "(eval)") == 0) {
		VALUE mesg, errat, bt2;
		extern VALUE rb_get_backtrace(VALUE info);
		ID id_mesg;

		CONST_ID(id_mesg, "mesg");
		errat = rb_get_backtrace(errinfo);
		mesg = rb_attr_get(errinfo, id_mesg);
		if (!NIL_P(errat) && TYPE(errat) == T_ARRAY &&
		    (bt2 = vm_backtrace(th, -2), RARRAY_LEN(bt2) > 0)) {
		    if (!NIL_P(mesg) && TYPE(mesg) == T_STRING && !RSTRING_LEN(mesg)) {
			if (OBJ_FROZEN(mesg)) {
			    VALUE m = rb_str_cat(rb_str_dup(RARRAY_PTR(errat)[0]), ": ", 2);
			    rb_ivar_set(errinfo, id_mesg, rb_str_append(m, mesg));
			}
			else {
			    rb_str_update(mesg, 0, 0, rb_str_new2(": "));
			    rb_str_update(mesg, 0, 0, RARRAY_PTR(errat)[0]);
			}
		    }
		    RARRAY_PTR(errat)[0] = RARRAY_PTR(bt2)[0];
		}
	    }
	    rb_exc_raise(errinfo);
	}
	JUMP_TAG(state);
    }
    return result;
}
Beispiel #27
0
void
rb_check_frozen(VALUE obj)
{
    if (OBJ_FROZEN(obj)) rb_error_frozen(rb_obj_classname(obj));
}
Beispiel #28
0
void
rb_add_method(VALUE klass, ID mid, NODE * node, int noex)
{
    NODE *body;

    if (NIL_P(klass)) {
	klass = rb_cObject;
    }
    if (rb_safe_level() >= 4 && (klass == rb_cObject || !OBJ_TAINTED(klass))) {
	rb_raise(rb_eSecurityError, "Insecure: can't define method");
    }
    if (!FL_TEST(klass, FL_SINGLETON) &&
	node && nd_type(node) != NODE_ZSUPER &&
	(mid == rb_intern("initialize") || mid == rb_intern("initialize_copy"))) {
	noex = NOEX_PRIVATE | noex;
    }
    else if (FL_TEST(klass, FL_SINGLETON) && node
	     && nd_type(node) == NODE_CFUNC && mid == rb_intern("allocate")) {
	rb_warn
	    ("defining %s.allocate is deprecated; use rb_define_alloc_func()",
	     rb_class2name(rb_iv_get(klass, "__attached__")));
	mid = ID_ALLOCATOR;
    }
    if (OBJ_FROZEN(klass)) {
	rb_error_frozen("class/module");
    }
    rb_clear_cache_by_id(mid);

    /*
     * NODE_METHOD (NEW_METHOD(body, klass, vis)):
     *   nd_body : method body   // (2) // mark
     *   nd_clss : klass         // (1) // mark
     *   nd_noex : visibility    // (3)
     *
     * NODE_FBODY (NEW_FBODY(method, alias)):
     *   nd_body : method (NODE_METHOD)  // (2) // mark
     *   nd_oid  : original id           // (1)
     *   nd_cnt  : alias count           // (3)
     */
    if (node) {
	body = NEW_FBODY(NEW_METHOD(node, klass, NOEX_WITH_SAFE(noex)), 0);
    }
    else {
	body = 0;
    }

    {
	/* check re-definition */
	st_data_t data;
	NODE *old_node;

	if (st_lookup(RCLASS_M_TBL(klass), mid, &data)) {
	    old_node = (NODE *)data;
	    if (old_node) {
		if (nd_type(old_node->nd_body->nd_body) == NODE_CFUNC) {
		    rb_vm_check_redefinition_opt_method(old_node);
		}
		if (RTEST(ruby_verbose) && node && old_node->nd_cnt == 0 && old_node->nd_body) {
		    rb_warning("method redefined; discarding old %s", rb_id2name(mid));
		}
	    }
	}
	if (klass == rb_cObject && node && mid == idInitialize) {
	    rb_warn("redefining Object#initialize may cause infinite loop");
	}

	if (mid == object_id || mid == __send__) {
	    if (node && nd_type(node) == RUBY_VM_METHOD_NODE) {
		rb_warn("redefining `%s' may cause serious problem",
			rb_id2name(mid));
	    }
	}
    }

    st_insert(RCLASS_M_TBL(klass), mid, (st_data_t) body);

    if (node && mid != ID_ALLOCATOR && ruby_running) {
	if (FL_TEST(klass, FL_SINGLETON)) {
	    rb_funcall(rb_iv_get(klass, "__attached__"), singleton_added, 1,
		       ID2SYM(mid));
	}
	else {
	    rb_funcall(klass, added, 1, ID2SYM(mid));
	}
    }
}
Beispiel #29
0
void rb_check_frozen(VALUE object) {
  if (OBJ_FROZEN(object)){
    rb_jt_error("rb_check_frozen failure case not implemented");
    abort();
  }
}
Beispiel #30
0
/*
 * call-seq:
 *    ctx.setup => Qtrue # first time
 *    ctx.setup => nil # thereafter
 *
 * This method is called automatically when a new SSLSocket is created.
 * Normally you do not need to call this method (unless you are writing an extension in C).
 */
static VALUE
ossl_sslctx_setup(VALUE self)
{
    SSL_CTX *ctx;
    X509 *cert = NULL, *client_ca = NULL;
    X509_STORE *store;
    EVP_PKEY *key = NULL;
    char *ca_path = NULL, *ca_file = NULL;
    int i, verify_mode;
    VALUE val;

    if(OBJ_FROZEN(self)) return Qnil;
    Data_Get_Struct(self, SSL_CTX, ctx);

#if !defined(OPENSSL_NO_DH)
    if (RTEST(ossl_sslctx_get_tmp_dh_cb(self))){
	SSL_CTX_set_tmp_dh_callback(ctx, ossl_tmp_dh_callback);
    }
    else{
	SSL_CTX_set_tmp_dh_callback(ctx, ossl_default_tmp_dh_callback);
    }
#endif
    SSL_CTX_set_ex_data(ctx, ossl_ssl_ex_ptr_idx, (void*)self);

    val = ossl_sslctx_get_cert_store(self);
    if(!NIL_P(val)){
	/*
         * WORKAROUND:
	 *   X509_STORE can count references, but
	 *   X509_STORE_free() doesn't care it.
	 *   So we won't increment it but mark it by ex_data.
	 */
        store = GetX509StorePtr(val); /* NO NEED TO DUP */
        SSL_CTX_set_cert_store(ctx, store);
        SSL_CTX_set_ex_data(ctx, ossl_ssl_ex_store_p, (void*)1);
    }

    val = ossl_sslctx_get_extra_cert(self);
    if(!NIL_P(val)){
	rb_block_call(val, rb_intern("each"), 0, 0, ossl_sslctx_add_extra_chain_cert_i, self);
    }

    /* private key may be bundled in certificate file. */
    val = ossl_sslctx_get_cert(self);
    cert = NIL_P(val) ? NULL : GetX509CertPtr(val); /* NO DUP NEEDED */
    val = ossl_sslctx_get_key(self);
    key = NIL_P(val) ? NULL : GetPKeyPtr(val); /* NO DUP NEEDED */
    if (cert && key) {
        if (!SSL_CTX_use_certificate(ctx, cert)) {
            /* Adds a ref => Safe to FREE */
            ossl_raise(eSSLError, "SSL_CTX_use_certificate:");
        }
        if (!SSL_CTX_use_PrivateKey(ctx, key)) {
            /* Adds a ref => Safe to FREE */
            ossl_raise(eSSLError, "SSL_CTX_use_PrivateKey:");
        }
        if (!SSL_CTX_check_private_key(ctx)) {
            ossl_raise(eSSLError, "SSL_CTX_check_private_key:");
        }
    }

    val = ossl_sslctx_get_client_ca(self);
    if(!NIL_P(val)){
	if(TYPE(val) == T_ARRAY){
	    for(i = 0; i < RARRAY_LEN(val); i++){
		client_ca = GetX509CertPtr(RARRAY_PTR(val)[i]);
        	if (!SSL_CTX_add_client_CA(ctx, client_ca)){
		    /* Copies X509_NAME => FREE it. */
        	    ossl_raise(eSSLError, "SSL_CTX_add_client_CA");
        	}
	    }
        }
	else{
	    client_ca = GetX509CertPtr(val); /* NO DUP NEEDED. */
            if (!SSL_CTX_add_client_CA(ctx, client_ca)){
		/* Copies X509_NAME => FREE it. */
        	ossl_raise(eSSLError, "SSL_CTX_add_client_CA");
            }
	}
    }

    val = ossl_sslctx_get_ca_file(self);
    ca_file = NIL_P(val) ? NULL : StringValuePtr(val);
    val = ossl_sslctx_get_ca_path(self);
    ca_path = NIL_P(val) ? NULL : StringValuePtr(val);
    if(ca_file || ca_path){
	if (!SSL_CTX_load_verify_locations(ctx, ca_file, ca_path))
	    rb_warning("can't set verify locations");
    }

    val = ossl_sslctx_get_verify_mode(self);
    verify_mode = NIL_P(val) ? SSL_VERIFY_NONE : NUM2INT(val);
    SSL_CTX_set_verify(ctx, verify_mode, ossl_ssl_verify_callback);
    if (RTEST(ossl_sslctx_get_client_cert_cb(self)))
	SSL_CTX_set_client_cert_cb(ctx, ossl_client_cert_cb);

    val = ossl_sslctx_get_timeout(self);
    if(!NIL_P(val)) SSL_CTX_set_timeout(ctx, NUM2LONG(val));

    val = ossl_sslctx_get_verify_dep(self);
    if(!NIL_P(val)) SSL_CTX_set_verify_depth(ctx, NUM2LONG(val));

    val = ossl_sslctx_get_options(self);
    if(!NIL_P(val)) SSL_CTX_set_options(ctx, NUM2LONG(val));
    rb_obj_freeze(self);

    val = ossl_sslctx_get_sess_id_ctx(self);
    if (!NIL_P(val)){
	StringValue(val);
	if (!SSL_CTX_set_session_id_context(ctx, (unsigned char *)RSTRING_PTR(val),
					    RSTRING_LEN(val))){
	    ossl_raise(eSSLError, "SSL_CTX_set_session_id_context:");
	}
    }

    if (RTEST(rb_iv_get(self, "@session_get_cb"))) {
	SSL_CTX_sess_set_get_cb(ctx, ossl_sslctx_session_get_cb);
	OSSL_Debug("SSL SESSION get callback added");
    }
    if (RTEST(rb_iv_get(self, "@session_new_cb"))) {
	SSL_CTX_sess_set_new_cb(ctx, ossl_sslctx_session_new_cb);
	OSSL_Debug("SSL SESSION new callback added");
    }
    if (RTEST(rb_iv_get(self, "@session_remove_cb"))) {
	SSL_CTX_sess_set_remove_cb(ctx, ossl_sslctx_session_remove_cb);
	OSSL_Debug("SSL SESSION remove callback added");
    }

#ifdef HAVE_SSL_SET_TLSEXT_HOST_NAME
    val = rb_iv_get(self, "@servername_cb");
    if (!NIL_P(val)) {
        SSL_CTX_set_tlsext_servername_callback(ctx, ssl_servername_cb);
	OSSL_Debug("SSL TLSEXT servername callback added");
    }
#endif

    return Qtrue;
}