Example #1
0
/*
 * Allocate a new and possibly larger storage space for an obj.
 */
struct obj *
realloc_obj(struct obj *obj, int oextra_size, void *oextra_src, int oname_size,
            const char *name)
{
    struct obj *otmp;

    otmp = newobj(oextra_size + oname_size, obj);

    if (oextra_size) {
        if (oextra_src)
            memcpy(otmp->oextra, oextra_src, oextra_size);
    } else {
        otmp->oattached = OATTACHED_NOTHING;
    }
    otmp->oxlth = oextra_size;
    otmp->onamelth = oname_size;

    if (oname_size) {
        if (name)
            strcpy(ONAME_MUTABLE(otmp), name);
    }

    /* !obj->olev means the obj is currently being restored and no pointer from 
       or to it is valid. Re-equipping, timer linking, etc. will happen
       elsewhere in that case. */
    if (obj->olev) {
        int i;
        if (obj->owornmask) {
            boolean save_twoweap = u.twoweap;

            /* unwearing the old instance will clear dual-wield mode if this
               object is either of the two weapons */
            setworn(NULL, obj->owornmask);
            setworn(otmp, otmp->owornmask);
            u.twoweap = save_twoweap;
        }

        /* replace obj with otmp */
        replace_object(obj, otmp);

        /* fix ocontainer pointers */
        if (Has_contents(obj)) {
            struct obj *inside;

            for (inside = obj->cobj; inside; inside = inside->nobj)
                inside->ocontainer = otmp;
        }

        /* move timers and light sources from obj to otmp */
        otmp->timed = 0;        /* not timed, yet */
        if (obj->timed)
            obj_move_timers(obj, otmp);
        otmp->lamplit = 0;      /* ditto */
        if (obj->lamplit)
            obj_move_light_source(obj, otmp);

        /* objects possibly being manipulated by multi-turn occupations which
           have been interrupted but might be subsequently resumed */
        for (i = 0; i <= tos_last_slot; i++) {
            if (obj == u.utracked[i])
                u.utracked[i] = otmp;
        }
        /* This is probably paranoia; it would only come up if an item can
           end up being specific-named as a result of trying to use it. */
        for (i = 0; i <= ttos_last_slot; i++) {
            if (obj == turnstate.tracked[i])
                turnstate.tracked[i] = otmp;
        }
    } else {
        /* During restore, floating objects are on the floating objects
           chain, /but/ may not have OBJ_FREE set. */
        otmp->where = obj->where;
        obj->where = OBJ_FREE;
        obj->timed = FALSE;
        obj->lamplit = FALSE;
    }
    /* obfree(obj, otmp); now unnecessary: no pointers on bill */

    dealloc_obj(obj);   /* let us hope nobody else saved a pointer */
    return otmp;
}
Example #2
0
/*
 * Allocate a new and possibly larger storage space for an obj.
 */
struct obj *realloc_obj(struct obj *obj, int oextra_size, void *oextra_src,
			int oname_size, const char *name)
{
	struct obj *otmp;

	otmp = newobj(oextra_size + oname_size);
	*otmp = *obj;	/* the cobj pointer is copied to otmp */
	if (oextra_size) {
	    if (oextra_src)
		memcpy(otmp->oextra, oextra_src, oextra_size);
	} else {
	    otmp->oattached = OATTACHED_NOTHING;
	}
	otmp->oxlth = oextra_size;
	otmp->onamelth = oname_size;
	
	if (oname_size) {
	    if (name)
		strcpy(ONAME(otmp), name);
	}

	/* !obj->olev means the obj is currently being restored and no pointer
	 * from or to it is valid. Re-equipping, timer linking, etc. will happen
	 * elsewhere in that case. */
	if (obj->olev) { 
	    if (obj->owornmask) {
		    boolean save_twoweap = u.twoweap;
		    /* unwearing the old instance will clear dual-wield mode
		    if this object is either of the two weapons */
		    setworn(NULL, obj->owornmask);
		    setworn(otmp, otmp->owornmask);
		    u.twoweap = save_twoweap;
	    }

	    /* replace obj with otmp */
	    replace_object(obj, otmp);

	    /* fix ocontainer pointers */
	    if (Has_contents(obj)) {
		    struct obj *inside;

		    for (inside = obj->cobj; inside; inside = inside->nobj)
			    inside->ocontainer = otmp;
	    }

	    /* move timers and light sources from obj to otmp */
	    otmp->timed = 0;	/* not timed, yet */
	    if (obj->timed) obj_move_timers(obj, otmp);
	    otmp->lamplit = 0;	/* ditto */
	    if (obj->lamplit) obj_move_light_source(obj, otmp);

	    /* objects possibly being manipulated by multi-turn occupations
	    which have been interrupted but might be subsequently resumed */
	    if (obj->oclass == FOOD_CLASS)
		food_substitution(obj, otmp);	/* eat food or open tin */
	    else if (obj->oclass == SPBOOK_CLASS)
		book_substitution(obj, otmp);	/* read spellbook */
	} else {
	    /* make sure dealloc_obj doesn't explode */
	    obj->where = OBJ_FREE;
	    obj->timed = FALSE;
	    obj->lamplit = FALSE;
	}
	/* obfree(obj, otmp);	now unnecessary: no pointers on bill */
	dealloc_obj(obj);	/* let us hope nobody else saved a pointer */
	return otmp;
}