예제 #1
0
void
show_floor(void)
{
    struct linked_list  *item;
    struct object   *obj;

    item = find_obj(hero.y, hero.x);

    if (item != NULL)
    {
        addmsg("%s onto ", terse ? "Moved" : "You moved");

        obj = OBJPTR(item);

        if (obj->next_obj != NULL)
            msg("a stack of things.");
        else if (obj->o_type == GOLD)
            msg("%d gold pieces.", obj->o_count);
        else
        {
            addmsg(inv_name(obj, TRUE));
            addmsg(".");
            endmsg();
        }
    }
}
예제 #2
0
/* ---------------------------
	 | Search default edit-obj |
	 --------------------------- */
int fm_inifld(OBJECT *tree, int start_fld)
{
    if (!start_fld)
        start_fld = find_obj(tree, 0);

    return start_fld;
}
예제 #3
0
/*
 * price_it:
 *	Price the object that the hero stands on
 */
bool price_it()
{
  static char *bargain[] = {
      "great bargain", "quality product", "exceptional find",
  };
  struct linked_list *item;
  struct object *obj;
  int worth;

  if (!open_market()) /* after buying hours */
    return FALSE;
  if ((item = find_obj(hero.y, hero.x)) == NULL)
    return FALSE;
  obj = OBJPTR(item);
  if (curprice == NOTPRICED) {
    worth = get_worth(obj);
    worth += 50 - rnd(100);
    if (worth < 25)
      worth = 25;
    worth *= 3;                       /* slightly expensive */
    curprice = worth;                 /* save price */
    strcpy(curpurch, obj->o_typname); /* save item */
  }
  msg("That %s is a %s for only %d pieces of gold", curpurch, bargain[rnd(3)],
      curprice);
  return TRUE;
}
예제 #4
0
bool plop_monster(int r, int c, Coord *cp)
{
    int y, x;
    int appear = 0;
    byte ch;

    for (y = r - 1; y <= r + 1; y++)
    {
        for (x = c - 1; x <= c + 1; x++)
        {
            Coord pos = { x, y };
            //Don't put a monster on top of the player.
            if (pos == game->hero().position() || offmap({ x,y }))
                continue;
            //Or anything else nasty
            if (step_ok(ch = game->level().get_tile_or_monster(pos)))//todo:bug: on mimic?
            {
                if (ch == SCROLL && is_scare_monster_scroll(find_obj(pos, false)))
                    continue;
                if (rnd(++appear) == 0) {
                    *cp = pos;
                }
            }
        }
    }

    return appear != 0;
}
예제 #5
0
VOID del_objindex(LONG tree, WORD obj)
{
	WORD	where;

	where = find_obj(tree, obj);
	if (where != NIL)
		del_index(where);
}
예제 #6
0
파일: tree.c 프로젝트: smintz/cluster
static struct ldap_object_node *
parse_element_tag(xmlNodePtr curr_node,
		  struct ldap_object_node **objs,
		  struct ldap_attr_node **attrs,
		  struct idinfo *ids)
{
	struct ldap_object_node *obj;
	char *n, *normalized;
	struct idval *v;
	int need_cn = 1;
	
	dbg_printf("Trying to parse element tag\n");
	n = (char *)xmlGetProp(curr_node, (xmlChar *)"name");
	normalized = normalize_name(n);
	v = id_find(ids, normalized, OBJ, 0);

	if (!v) {
		v = zalloc(sizeof(*v));
		v->name = normalized;
		v->rawname = n;
		v->type = OBJ;
		id_insert(ids, v);
	}

	obj = find_obj(*objs, v->name);

	if (!obj) {
		obj = zalloc(sizeof(*obj));
		obj->name = v->name;
		obj->idval = v;
		obj->next = *objs;
		*objs = obj;
		dbg_printf("New object class %s \n",obj->name);
	}

	find_optional_attributes(curr_node->xmlChildrenNode, 0,
				 obj, attrs, ids);
	find_required_attributes(curr_node->xmlChildrenNode,
				 obj, attrs, ids);

	if (find_meta_attr_byname(obj->required_attrs, "name") ||
	    find_meta_attr_byname(obj->required_attrs, "cn")) {
		need_cn = 0;
	}

	if (need_cn &&
	    (find_meta_attr_byname(obj->optional_attrs, "name") ||
	     find_meta_attr_byname(obj->optional_attrs, "cn"))) {
		need_cn = 0;
	}

	if (need_cn) {
		dbg_printf("Object class might %s need 'MUST ( cn )' for proper LDIF\n", obj->name);
		obj->need_cn = 1;
	}

	return obj;
}
예제 #7
0
파일: room_reset.c 프로젝트: KaSt/nereamud
//
// handles "find" and "purge" in one function
bool try_reset_old_object(RESET_DATA *reset, void *initiator,int initiator_type,
			  int reset_cmd, const char *locale) {
  const char *fullkey = get_fullkey_relative(resetGetArg(reset), locale);
  OBJ_DATA       *obj = NULL;

  // is it the room?
  if(initiator_type == INITIATOR_ROOM)
    obj = find_obj(NULL, roomGetContents(initiator),  1, NULL, fullkey, FALSE);
  // is it in a container?
  else if(initiator_type == INITIATOR_IN_OBJ)
    obj = find_obj(NULL, objGetContents(initiator),   1, NULL, fullkey, FALSE);
  // is it in a person's inventory?
  else if(initiator_type == INITIATOR_IN_MOB)
    obj = find_obj(NULL, charGetInventory(initiator), 1, NULL, fullkey, FALSE);
  // is it in a person's equipment?
  else if(initiator_type == INITIATOR_ON_MOB) {
    LIST *eq = bodyGetAllEq(charGetBody(initiator));
    obj = find_obj(NULL, eq, 1, NULL, fullkey, FALSE);
    deleteList(eq);
  }

  // if we didn't find it, return false
  if(obj == NULL)
    return FALSE;

  // now, run our reset sscripts
  resetRunOn(reset->on,   obj, INITIATOR_ON_OBJ,   locale);
  resetRunOn(reset->in,   obj, INITIATOR_IN_OBJ,   locale);
  resetRunOn(reset->then, obj, INITIATOR_THEN_OBJ, locale);

  // if this is a purge and it wasn't our initiator, kill it
  // if we purge our initiator, we might run into some problems
  if(obj != initiator && reset_cmd == RESET_PURGE_OBJECT)
    extract_obj(obj);
    
  return TRUE;
}
예제 #8
0
static rc_t on_enter_path( const reply_obj * obj, void * data )
{
    rc_t rc = 0;
    if ( obj != NULL && data != NULL )
    {
        reply_obj_list * list = data;
        reply_obj * found = find_obj( list, obj->id );
        if ( found != NULL )
        {
            if ( found->path != NULL ) StringWhack( found->path );
            rc = StringCopy( &found->path, obj->path );
        }
    }
    return rc;
}
예제 #9
0
int main(int argc, char** argv) {

  if (isatty(2) && !getenv("AFL_QUIET")) {

#ifdef USE_TRACE_PC
    SAYF(cCYA "afl-clang-fast [tpcg] " cBRI VERSION  cRST " by <*****@*****.**>\n");
#else
    SAYF(cCYA "afl-clang-fast " cBRI VERSION  cRST " by <*****@*****.**>\n");
#endif /* ^USE_TRACE_PC */

  }

  if (argc < 2) {

    SAYF("\n"
         "This is a helper application for afl-fuzz. It serves as a drop-in replacement\n"
         "for clang, letting you recompile third-party code with the required runtime\n"
         "instrumentation. A common use pattern would be one of the following:\n\n"

         "  CC=%s/afl-clang-fast ./configure\n"
         "  CXX=%s/afl-clang-fast++ ./configure\n\n"

         "In contrast to the traditional afl-clang tool, this version is implemented as\n"
         "an LLVM pass and tends to offer improved performance with slow programs.\n\n"

         "You can specify custom next-stage toolchain via AFL_CC and AFL_CXX. Setting\n"
         "AFL_HARDEN enables hardening optimizations in the compiled code.\n\n",
         BIN_PATH, BIN_PATH);

    exit(1);

  }


  find_obj(argv[0]);

  edit_params(argc, argv);

  execvp(cc_params[0], (char**)cc_params);

  FATAL("Oops, failed to execute '%s' - check your PATH", cc_params[0]);

  return 0;

}
예제 #10
0
파일: pack.c 프로젝트: Elronnd/rogomatic
void
pick_up(char ch)
{
    THING *obj;

    if (on(player, ISLEVIT))
	return;

    obj = find_obj(hero.y, hero.x);
    if (move_on)
	move_msg(obj);
    else
	switch (ch)
	{
	    case GOLD:
		if (obj == NULL)
		    return;
		money(obj->o_goldval);
		detach(lvl_obj, obj);
		discard(obj);
		proom->r_goldval = 0;
		break;
	    default:
#ifdef MASTER
		debug("Where did you pick a '%s' up???", unctrl(ch));
#endif
	    case ARMOR:
	    case POTION:
	    case FOOD:
	    case WEAPON:
	    case SCROLL:	
	    case AMULET:
	    case RING:
	    case STICK:
		add_pack((THING *) NULL, FALSE);
		break;
	}
}
예제 #11
0
/* **Find the first edit-object** */
int fm_inifld(OBJECT *tree, int start_fld)
{
 if(start_fld==0)
   start_fld=find_obj(tree, 0, FMD_FORWARD);
 return(start_fld);
}
예제 #12
0
/*
 * add_pack:
 *	Pick up an object and add it to the pack.  If the argument is non-null
 * use it as the linked_list pointer instead of gettting it off the ground.
 */
void
add_pack(struct linked_list *item, int silent)
{
    struct linked_list *ip, *lp;
    struct object *obj, *op;
    int exact, from_floor;

    if (item == NULL)
    {
	from_floor = TRUE;
	if ((item = find_obj(hero.y, hero.x)) == NULL)
	    return;
    }
    else
	from_floor = FALSE;
    obj = (struct object *) ldata(item);
    /*
     * Link it into the pack.  Search the pack for a object of similar type
     * if there isn't one, stuff it at the beginning, if there is, look for one
     * that is exactly the same and just increment the count if there is.
     * it  that.  Food is always put at the beginning for ease of access, but
     * is not ordered so that you can't tell good food from bad.  First check
     * to see if there is something in thr same group and if there is then
     * increment the count.
     */
    if (obj->o_group)
    {
	for (ip = pack; ip != NULL; ip = next(ip))
	{
	    op = (struct object *) ldata(ip);
	    if (op->o_group == obj->o_group)
	    {
		/*
		 * Put it in the pack and notify the user
		 */
		op->o_count++;
		if (from_floor)
		{
		    detach(lvl_obj, item);
		    mvaddch(hero.y, hero.x,
			(roomin(&hero) == NULL ? PASSAGE : FLOOR));
		}
		discard(item);
		item = ip;
		goto picked_up;
	    }
	}
    }
    /*
     * Check if there is room
     */
    if (inpack == MAXPACK-1)
    {
	msg("You can't carry anything else.");
	return;
    }
    /*
     * Check for and deal with scare monster scrolls
     */
    if (obj->o_type == SCROLL && obj->o_which == S_SCARE)
	if (obj->o_flags & ISFOUND)
	{
	    msg("The scroll turns to dust as you pick it up.");
	    detach(lvl_obj, item);
	    mvaddch(hero.y, hero.x, FLOOR);
	    return;
	}
	else
	    obj->o_flags |= ISFOUND;

    inpack++;
    if (from_floor)
    {
	detach(lvl_obj, item);
	mvaddch(hero.y, hero.x, (roomin(&hero) == NULL ? PASSAGE : FLOOR));
    }
    /*
     * Search for an object of the same type
     */
    exact = FALSE;
    for (ip = pack; ip != NULL; ip = next(ip))
    {
	op = (struct object *) ldata(ip);
	if (obj->o_type == op->o_type)
	    break;
    }
    if (ip == NULL)
    {
	/*
	 * Put it at the end of the pack since it is a new type
	 */
	for (ip = pack; ip != NULL; ip = next(ip))
	{
	    op = (struct object *) ldata(ip);
	    if (op->o_type != FOOD)
		break;
	    lp = ip;
	}
    }
    else
    {
	/*
	 * Search for an object which is exactly the same
	 */
	while (ip != NULL && op->o_type == obj->o_type)
	{
	    if (op->o_which == obj->o_which)
	    {
		exact = TRUE;
		break;
	    }
	    lp = ip;
	    if ((ip = next(ip)) == NULL)
		break;
	    op = (struct object *) ldata(ip);
	}
    }
    if (ip == NULL)
    {
	/*
	 * Didn't find an exact match, just stick it here
	 */
	if (pack == NULL)
	    pack = item;
	else
	{
	    lp->l_next = item;
	    item->l_prev = lp;
	    item->l_next = NULL;
	}
    }
    else
    {
	/*
	 * If we found an exact match.  If it is a potion, food, or a 
	 * scroll, increase the count, otherwise put it with its clones.
	 */
	if (exact && ISMULT(obj->o_type))
	{
	    op->o_count++;
	    discard(item);
	    item = ip;
	    goto picked_up;
	}
	if ((item->l_prev = prev(ip)) != NULL)
	    item->l_prev->l_next = item;
	else
	    pack = item;
	item->l_next = ip;
	ip->l_prev = item;
    }
picked_up:
    /*
     * Notify the user
     */
    obj = (struct object *) ldata(item);
    if (notify && !silent)
    {
	if (!terse)
	    addmsg("You now have ");
	msg("%s (%c)", inv_name(obj, !terse), pack_char(obj));
    }
    if (obj->o_type == AMULET)
	amulet = TRUE;
}
예제 #13
0
char *pdf_parse_string(struct pdf_struct *pdf, struct pdf_obj *obj, const char *objstart, size_t objsize, const char *str, char **endchar, struct pdf_stats_metadata *meta)
{
    const char *q = objstart;
    char *p1, *p2;
    size_t len, checklen;
    char *res = NULL;
    uint32_t objid;
    size_t i;

    /*
     * Yes, all of this is required to find the start and end of a potentially UTF-* string
     *
     * First, find the key of the key/value pair we're looking for in this object.
     * Second, determine whether the value points to another object (NOTE: this is sketchy behavior)
     * Third, attempt to determine if we're ASCII or UTF-*
     * If we're ASCII, just copy the ASCII string into a new heap-allocated string and return that
     * Fourth, Attempt to decode from UTF-* to UTF-8
     */

    if (str) {
        checklen = strlen(str);

        if (objsize < strlen(str) + 3)
            return NULL;

        for (p1=(char *)q; (size_t)(p1 - q) < objsize-checklen; p1++)
            if (!strncmp(p1, str, checklen))
                break;

        if ((size_t)(p1 - q) == objsize - checklen)
            return NULL;

        p1 += checklen;
    } else {
        p1 = (char *)q;
    }

    while ((size_t)(p1 - q) < objsize && isspace(p1[0]))
        p1++;

    if ((size_t)(p1 - q) == objsize)
        return NULL;

    /*
     * If str is non-null:
     *     We should be at the start of the string, minus 1
     * Else:
     *     We should be at the start of the string
     */

    p2 = (char *)(q + objsize);
    if (is_object_reference(p1, &p2, &objid)) {
        struct pdf_obj *newobj;
        char *begin, *p3;
        STATBUF sb;
        uint32_t objflags;
        int fd;
        size_t objsize2;

        newobj = find_obj(pdf, obj, objid);
        if (!(newobj))
            return NULL;

        if (newobj == obj)
            return NULL;

        /* 
         * If pdf_handlename hasn't been called for this object,
         * then parse the object prior to extracting it
         */
        if (!(newobj->statsflags & OBJ_FLAG_PDFNAME_DONE))
            pdf_parseobj(pdf, newobj);

        /* Extract the object. Force pdf_extract_obj() to dump this object. */
        objflags = newobj->flags;
        newobj->flags |= (1 << OBJ_FORCEDUMP);

        if (pdf_extract_obj(pdf, newobj, PDF_EXTRACT_OBJ_NONE) != CL_SUCCESS)
            return NULL;

        newobj->flags = objflags;

        if (!(newobj->path))
            return NULL;

        fd = open(newobj->path, O_RDONLY);
        if (fd == -1) {
            cli_unlink(newobj->path);
            free(newobj->path);
            newobj->path = NULL;
            return NULL;
        }

        if (FSTAT(fd, &sb)) {
            close(fd);
            cli_unlink(newobj->path);
            free(newobj->path);
            newobj->path = NULL;
            return NULL;
        }

        if (sb.st_size) {
            begin = calloc(1, sb.st_size+1);
            if (!(begin)) {
                close(fd);
                cli_unlink(newobj->path);
                free(newobj->path);
                newobj->path = NULL;
                return NULL;
            }

            if (read(fd, begin, sb.st_size) != sb.st_size) {
                close(fd);
                cli_unlink(newobj->path);
                free(newobj->path);
                newobj->path = NULL;
                free(begin);
                return NULL;
            }

            p3 = begin;
            objsize2 = sb.st_size;
            while ((size_t)(p3 - begin) < objsize2 && isspace(p3[0])) {
                p3++;
                objsize2--;
            }

            switch (*p3) {
                case '(':
                case '<':
                    res = pdf_parse_string(pdf, obj, p3, objsize2, NULL, NULL, meta);
                    break;
                default:
                    res = pdf_finalize_string(pdf, obj, begin, objsize2);
                    if (!res) {
                        res = cli_calloc(1, objsize2+1);
                        if (!(res)) {
                            close(fd);
                            cli_unlink(newobj->path);
                            free(newobj->path);
                            newobj->path = NULL;
                            free(begin);
                            return NULL;
                        }
                        memcpy(res, begin, objsize2);
                        res[objsize2] = '\0';

                        if (meta) {
                            meta->length = objsize2;
                            meta->obj = obj;
                            meta->success = 0;
                        }
                    } else if (meta) {
                        meta->length = strlen(res);
                        meta->obj = obj;
                        meta->success = 1;
                    }
            }
            free(begin);
        }

        close(fd);
        cli_unlink(newobj->path);
        free(newobj->path);
        newobj->path = NULL;

        if (endchar)
            *endchar = p2;

        return res;
    }

    if (*p1 == '<') {
        /* Hex string */

        p2 = p1+1;
        while ((size_t)(p2 - q) < objsize && *p2 != '>')
            p2++;

        if ((size_t)(p2 - q) == objsize) {
            return NULL;
        }


        res = pdf_finalize_string(pdf, obj, p1, (p2 - p1) + 1);
        if (!res) {
            res = cli_calloc(1, (p2 - p1) + 2);
            if (!(res))
                return NULL;
            memcpy(res, p1, (p2 - p1) + 1);
            res[(p2 - p1) + 1] = '\0';

            if (meta) {
                meta->length = (p2 - p1) + 1;
                meta->obj = obj;
                meta->success = 0;
            }
        } else if (meta) {
            meta->length = strlen(res);
            meta->obj = obj;
            meta->success = 1;
        }

        if (res && endchar)
            *endchar = p2;

        return res;
    }

    /* We should be at the start of a string literal (...) here */
    if (*p1 != '(')
        return NULL;

    /* Make a best effort to find the end of the string and determine if UTF-* */
    p2 = ++p1;
    while (p2 < objstart + objsize) {
        int shouldbreak=0;

        switch (*p2) {
            case '\\':
                p2++;
                break;
            case ')':
                shouldbreak=1;
                break;
        }

        if (shouldbreak) {
            p2--;
            break;
        }

        p2++;
    }

    if (p2 == objstart + objsize)
        return NULL;

    len = (size_t)(p2 - p1) + 1;

    res = pdf_finalize_string(pdf, obj, p1, len);
    if (!res) {
        res = cli_calloc(1, len+1);
        if (!(res))
            return NULL;
        memcpy(res, p1, len);
        res[len] = '\0';

        if (meta) {
            meta->length = len;
            meta->obj = obj;
            meta->success = 0;
        }
    } else if (meta) {
        meta->length = strlen(res);
        meta->obj = obj;
        meta->success = 1;
    }

    if (res && endchar)
        *endchar = p2;

    return res;
}
예제 #14
0
파일: pack.c 프로젝트: ajpaulson/srogue11
/*
 * add_pack:
 * Pick up an object and add it to the pack.  If the argument
 * is non-null use it as the linked_list pointer instead of
 * getting it off the ground.
 */
bool add_pack(struct linked_list *item,bool silent)
{
	struct linked_list *ip, *lp;
	struct object *obj, *op;
	bool from_floor;
	char delchar;

	if (player.t_room == NULL)
		delchar = PASSAGE;
	else
		delchar = FLOOR;
	if (item == NULL) {
		from_floor = TRUE;
		if ((item = find_obj(hero.y, hero.x)) == NULL) {
			mpos = 0;
			msg("That object must have been an illusion.");
			mvaddch(hero.y, hero.x, delchar);
			return FALSE;
		}
		/*
		 * Check for scare monster scrolls
		 */
		obj = OBJPTR(item);
		if (obj->o_type == SCROLL && obj->o_which == S_SCARE) {
			if (o_on(obj,ISFOUND)) {
				msg("The scroll turns to dust as you pick it up.");
				detach(lvl_obj, item);
				discard(item);
				mvaddch(hero.y, hero.x, delchar);	
				return FALSE;
			}
		}
	}
	else
		from_floor = FALSE;
	obj = OBJPTR(item);
	/*
	 * See if this guy can carry any more weight
	 */
	if (itemweight(obj) + him->s_pack > him->s_carry) {
		msg("You can't carry that %s.", obj->o_typname);
		return FALSE;
	}
	/*
	 * Check if there is room
	 */
	if (packvol + obj->o_vol > V_PACK) {
		msg("That %s won't fit in your pack.", obj->o_typname);
		return FALSE;
	}
	if (from_floor) {
		detach(lvl_obj, item);
		mvaddch(hero.y, hero.x, delchar);
	}
	item->l_prev = NULL;
	item->l_next = NULL;
	setoflg(obj, ISFOUND);
	/*
	 * start looking thru pack to find the start of items
	 * with the same type.
	 */
	lp = pack;
	for (ip = pack; ip != NULL; ip = next(ip)) {
		op = OBJPTR(ip);
		/*
		 * If we find a matching type then quit.
		 */
		if (op->o_type == obj->o_type)
			break;
		if (next(ip) != NULL)
			lp = next(lp);		/* update "previous" entry */
	}
	/*
	 * If the pack was empty, just stick the item in it.
	 */
	if (pack == NULL) {
		pack = item;
		item->l_prev = NULL;
	}
	/*
	 * If we looked thru the pack, but could not find an
	 * item of the same type, then stick it at the end,
	 * unless it was food, then put it in front.
	 */
	else if (ip == NULL) {
		if (obj->o_type == FOOD) {	/* insert food at front */
			item->l_next = pack;
			pack->l_prev = item;
			pack = item;
			item->l_prev = NULL;
		}
		else {						/* insert other stuff at back */
			lp->l_next = item;
			item->l_prev = lp;
		}
	}
	/*
	 * Here, we found at least one item of the same type.
	 * Look thru these items to see if there is one of the
	 * same group. If so, increment the count and throw the
	 * new item away. If not, stick it at the end of the
	 * items with the same type. Also keep all similar
	 * objects near each other, like all identify scrolls, etc.
	 */
	else {
		struct linked_list **save;

		while (ip != NULL && op->o_type == obj->o_type) {
			if (op->o_group == obj->o_group) {
				if (op->o_flags == obj->o_flags) {
					op->o_count++;
					discard(item);
					item = ip;
					goto picked_up;
				}
				else {
					goto around;
				}
			}
			if (op->o_which == obj->o_which) {
				if (obj->o_type == FOOD)
					ip = next(ip);
				break;
			}
around:
			ip = next(ip);
			if (ip != NULL) {
				op = OBJPTR(ip);
				lp = next(lp);
			}
		}
		/*
		 * If inserting into last of group at end of pack,
		 * just tack on the end.
		 */
		if (ip == NULL) {
			lp->l_next = item;
			item->l_prev = lp;
		}
		/*
		 * Insert into the last of a group of objects
		 * not at the end of the pack.
		 */
		else {
			save = &((ip->l_prev)->l_next);
			item->l_next = ip;
			item->l_prev = ip->l_prev;
			ip->l_prev = item;
			*save = item;
		}
	}
picked_up:
	obj = OBJPTR(item);
	if (!silent)
		msg("%s (%c)",inv_name(obj,FALSE),pack_char(obj));
	if (obj->o_type == AMULET)
		amulet = TRUE;
	updpack();				/* new pack weight & volume */
	return TRUE;
}
예제 #15
0
파일: pack.c 프로젝트: Elronnd/rogomatic
void
add_pack(THING *obj, bool silent)
{
    THING *op, *lp;
    bool from_floor;

    from_floor = FALSE;
    if (obj == NULL)
    {
	if ((obj = find_obj(hero.y, hero.x)) == NULL)
	    return;
	from_floor = TRUE;
    }

    /*
     * Check for and deal with scare monster scrolls
     */
    if (obj->o_type == SCROLL && obj->o_which == S_SCARE)
	if (obj->o_flags & ISFOUND)
	{
	    detach(lvl_obj, obj);
	    mvaddch(hero.y, hero.x, floor_ch());
	    chat(hero.y, hero.x) = (proom->r_flags & ISGONE) ? PASSAGE : FLOOR;
	    discard(obj);
	    msg("the scroll turns to dust as you pick it up");
	    return;
	}

    if (pack == NULL)
    {
	pack = obj;
	obj->o_packch = pack_char();
	inpack++;
    }
    else
    {
	lp = NULL;
	for (op = pack; op != NULL; op = next(op))
	{
	    if (op->o_type != obj->o_type)
		lp = op;
	    else
	    {
		while (op->o_type == obj->o_type && op->o_which != obj->o_which)
		{
		    lp = op;
		    if (next(op) == NULL)
			break;
		    else
			op = next(op);
		}
		if (op->o_type == obj->o_type && op->o_which == obj->o_which)
		{
		    if (ISMULT(op->o_type))
		    {
			if (!pack_room(from_floor, obj))
			    return;
			op->o_count++;
dump_it:
			discard(obj);
			obj = op;
			lp = NULL;
			goto out;
		    }
		    else if (obj->o_group)
		    {
			lp = op;
			while (op->o_type == obj->o_type
			    && op->o_which == obj->o_which
			    && op->o_group != obj->o_group)
			{
			    lp = op;
			    if (next(op) == NULL)
				break;
			    else
				op = next(op);
			}
			if (op->o_type == obj->o_type
			    && op->o_which == obj->o_which
			    && op->o_group == obj->o_group)
			{
				op->o_count += obj->o_count;
				inpack--;
				if (!pack_room(from_floor, obj))
				    return;
				goto dump_it;
			}
		    }
		    else
			lp = op;
		}
out:
		break;
	    }
	}

	if (lp != NULL)
	{
	    if (!pack_room(from_floor, obj))
		return;
	    else
	    {
		obj->o_packch = pack_char();
		next(obj) = next(lp);
		prev(obj) = lp;
		if (next(lp) != NULL)
		    prev(next(lp)) = obj;
		next(lp) = obj;
	    }
	}
    }

    obj->o_flags |= ISFOUND;

    /*
     * If this was the object of something's desire, that monster will
     * get mad and run at the hero.
     */
    for (op = mlist; op != NULL; op = next(op))
	if (op->t_dest == &obj->o_pos)
	    op->t_dest = &hero;

    if (obj->o_type == AMULET)
	amulet = TRUE;
    /*
     * Notify the user
     */
    if (!silent)
    {
	if (!terse)
	    addmsg("you now have ");
	msg("%s (%c)", inv_name(obj, !terse), obj->o_packch);
    }
}
예제 #16
0
int
add_pack(struct linked_list *item, int print_message)
{
    struct object   *obj, *op;
    int from_floor;

    if (item == NULL)
    {
        from_floor = TRUE;

        if ((item = find_obj(hero.y, hero.x)) == NULL)
        {
            msg("Nothing to pick up.");
            return(FALSE);
        }
    }
    else
        from_floor = FALSE;

    if (from_floor)
    {
        item = get_stack(item);

        if (!item)
            return(FALSE);
    }

    obj = OBJPTR(item);

    /* If it is gold, just add its value to rogue's purse and get rid of */

    if (obj->o_type == GOLD)
    {
        struct linked_list  *mitem;
        struct thing    *tp;

        if (print_message)
        {
            if (!terse)
                addmsg("You found ");

            msg("%d gold pieces.", obj->o_count);
        }

        /*
         * First make sure no greedy monster is after this gold. If
         * so, make the monster run after the rogue instead.
         */

        for (mitem = mlist; mitem != NULL; mitem = next(mitem))
        {
            tp = THINGPTR(mitem);

            if (tp->t_horde==obj)
            {
                tp->t_ischasing = TRUE;
                tp->t_chasee = &player;
                tp->t_horde  = NULL;
            }
        }

        /*
         * This will cause problems if people are able to drop and
         * pick up gold, or when GOLDSTEAL monsters are killed.
         */

        /* Thieves get EXP for gold they pick up */

        if (player.t_ctype == C_THIEF)
        {
            pstats.s_exp += obj->o_count / 4;
            check_level();
        }

        purse += obj->o_count;

        if (from_floor)
            rem_obj(item, TRUE);    /* Remove object from the level */

        return (TRUE);
    }

    /* see if he can carry any more weight */

    if (itemweight(obj) + pstats.s_pack > pstats.s_carry)
    {
        msg("Too much for you to carry.");

        if (print_message)
        {
            msg("%s onto %s", terse ? "Moved" : "You moved",
                inv_name(obj, LOWERCASE));
        }

        return(FALSE);
    }

    /*
     * Link it into the pack. If the item can be grouped, try to find its
     * neighbors and bump the count. A special case is food, which can't
     * be grouped, but an exact match allows the count to get
     * incremented.
     */

    if ((op = apply_to_bag(pack, obj->o_type, bff_group, NULL, obj)) != NULL)
    {
        op->o_count += obj->o_count;    /* add it to the rest */

        if (from_floor)
            rem_obj(item, FALSE);

        pack_report(op, print_message, "You now have ");

        return(TRUE);
    }

    /* Check for and deal with scare monster scrolls */

    if (obj->o_type == SCROLL && obj->o_which == S_SCARE)
        if (obj->o_flags & ISCURSED)
        {
            msg("The scroll turns to dust as you pick it up.");
            rem_obj(item, TRUE);
            return(TRUE);
        }

    /* Check if there is room */

    if (count_bag(pack, obj->o_type, NULL) == max_print())
    {
        msg("You have no room for more %s.", name_type(obj->o_type));

        if (print_message)
        {
            obj = OBJPTR(item);
            msg("%s onto %s.", terse ? "Moved" : "You moved",
                inv_name(obj, LOWERCASE));
        }

        return(FALSE);
    }

    /*
     * finally, add the new item to the bag, and free up the linked list
     * on top of it.
     */

    if (from_floor)
        rem_obj(item, FALSE);

    push_bag(&pack, obj);
    pack_report(obj, print_message, "You now have ");
    ur_free(item);

    return(TRUE);      /* signal success */
}
예제 #17
0
파일: conf.c 프로젝트: leevon/rhizel
cfg_st *cfg_load(char *path)
{
    FILE *fp = fopen(path, "r");
    if (NULL == fp)
    {
      return NULL;
    }

    struct cfg_section *sec_head = NULL;
    struct cfg_section *sec_prev = NULL;
    struct cfg_section *sec_curr = NULL;

    struct cfg_obj *obj_curr = NULL;
    struct cfg_obj *obj_prev = NULL;

    char *line = NULL;
    size_t   n  = 0;
    ssize_t len = 0;

    while ((len = _readline(&line, &n, fp)) != -1)
    {
        char *s = line;
        #ifdef __DEBUG__
          printf("1_readline:%s\n",s);
        #endif
        if (is_comment(&s))
            continue;
        len = strlen(s);

        if (len>2 && s[0]=='[' && s[len-1]==']')
        {
            char *name = s + 1;
            *(name+len-1-1) = '\0';
            trim(name);

            if ((sec_curr = find_section(sec_head, name)) == NULL)
            {
                if ((sec_curr = create_section(sec_head, name)) == NULL)
                {
                    free(line);
                    return NULL;
                }

                if (sec_head == NULL)
                    sec_head = sec_curr;
                if (sec_prev != NULL)
                    sec_prev->next = sec_curr;

                sec_prev = sec_curr;
                obj_prev = NULL;
            }
            else
            {
                obj_prev = sec_curr->obj;
                while (obj_prev->next != NULL)
                    obj_prev = obj_prev->next;
            }
            continue;
        }

        char *delimiter = strchr(s, '=');
        if (delimiter == NULL)
            continue;
        *delimiter = '\0';

        char *name = s;
        trim(name);

        char *value = delimiter + 1;
        delimiter = strchr(value, '#');
        if (NULL != delimiter)
        {
          *delimiter = '\0';
        }
        trim(value);

        if (sec_curr == NULL)
        {
            if ((sec_curr = create_section(sec_head, "global")) == NULL)
            {
                free(line);

                return NULL;
            }

            if (sec_head == NULL)
                sec_head = sec_curr;
            sec_prev = sec_curr;
            obj_prev = NULL;
        }

        if ((obj_curr = find_obj(sec_curr, name)) == NULL)
        {
            obj_curr = create_obj(sec_head, name, value);
            if (obj_curr == NULL)
            {
                free(line);

                return NULL;
            }

            if (obj_prev)
                obj_prev->next = obj_curr;
            if (sec_curr->obj == NULL)
                sec_curr->obj = obj_curr;

            obj_prev = obj_curr;
        }
        else
        {
            char *old_value = obj_curr->value;

            if ((obj_curr->value = strdup(value)) == NULL)
            {
                cfg_free(sec_head);

                free(line);

                return NULL;
            }

            free(old_value);
        }
    }

    free(line);
    fclose(fp);

    if (sec_head == NULL)
    {
        if ((sec_head = calloc(1, sizeof(struct cfg_section))) == NULL)
            return NULL;
    }
    #ifdef __DEBUG__
      ini_print(sec_head);
    #endif
    
    return sec_head;
}
예제 #18
0
/* ................................................................
 * Handle user interaction with a form in open window `w'.
 *
 * Initial conditions are as follows:
 * w->x is the address of the form.
 * window is open, with appropriate WINFO rects & coordinates set
 * form is drawn within window, at correct virtual coordinates
 * ROOT object of form has correct x,y coordinates
 *
 * This routine works just like form_do, but dispatches window
 * events, redrawing and fixing up the object tree as appropriate,
 * and maintaining the various rects and coordinates in the WINFO struct.
 *
 * Returns exit object selected, |= 0x8000 if double clicked a TOUCHEXIT,
 * OR -1 if a message was received which couldn't be handled.
 * In the latter case, the `puntmsg' array is filled with the message buffer
 * which xform_do() couldn't handle, and the application is responsible for
 * picking up where xform_do() left off.  A cop-out, I know.
 *
 * NOTE: form_dial( FMD_START,... ) and form_dial( FMD_FINISH,... )
 *		should NOT be used with xform_do().
 *
 * User defined objects could cause problems with this routine, as
 * the boundary of the object may lie outside the window coordinates.
 * Caveat programmer.
 */
WORD
cdecl
xform_do( OBJECT *tree, WORD start_field, WORD puntmsg[] )
{
	WORD	next_obj, edit_obj, idx;
	BOOLEAN	cont, doedit;
	WORD	event;
	MRETS	m;
	WORD	key, clicks;
	DIRS	direction; /* form_keybd */
	GRECT	rect;
		
	cpx_tree = tree;
	SetAccCloseState( FALSE );
	SetWmCloseState( FALSE );
	/*
	 * Get the next editable object
	 */
	if( start_field == 0 )
		next_obj = find_obj( tree, 0, FORWARD );
	else
		next_obj = start_field;

	edit_obj = 0;
	cont = TRUE;
	
	cursor = FALSE;
	
	while( cont ) {

		/*
		 * Put the cursor in the edit field
		 * Note: This is skipped if there is only one field.
		 */
		if( (next_obj != 0) && (edit_obj != next_obj) ) {
			edit_obj = next_obj;
			next_obj = 0;
			doedit = can_edit( tree, edit_obj );
			if( doedit && !cursor )
			{
				objc_edit( tree, edit_obj, 0, (int *)&idx, ED_INIT );
				cursor = TRUE;
			}	
		}
		wind_update( FALSE );
		/*
		 * Wait...
		 */
		event = Evnt_multi( MU_KEYBD|MU_BUTTON|MU_MESAG, 2, 1, 1,
							NULL, NULL, msg, 0L, &m, &key, &clicks );
		wind_update( TRUE );

		if( EvMessage() ) {
			switch( MsgType(msg) ) {
				case AC_OPEN:   acc_open( (int *)msg );
						break;
						
				case WM_TOPPED:
				case WM_NEWTOP:
					        Wm_Topped( ( int *)msg );
						doedit = can_edit( tree, edit_obj );
					        if( doedit && !cursor )
					        {
					           objc_edit( tree, edit_obj, 0, (int *)&idx, ED_INIT );
						   cursor = TRUE;
					        }
						break;
						
				case WM_SIZED:
					doedit = can_edit( tree, edit_obj );
					
				/* fall through */
				case WM_MOVED:	/* if moving, that means we are on top, therefore, cursor is already on */
						doedit = can_edit( tree, edit_obj );
						if( !doedit )
							cursor = FALSE;
				case WM_REDRAW:
				case WM_FULLED:
				case WM_ARROWED:
				case WM_HSLID:
				case WM_VSLID:
				/* redraw 'n' shit */
						
					if( edit_obj && ( msg[0] == WM_REDRAW ))
					{
					    NoEdit( edit_obj );
					    rect = ObRect( edit_obj );
					    objc_offset( tree, edit_obj, &rect.g_x, &rect.g_y );

					    /* The offsets will take care of the blinking cursor
					     * area that needs to be redraw to erase it.
					     */
					    rect.g_y -= 3;
					    rect.g_w += 3;
					    rect.g_h += 6;

					    /* Clip the rectangle to the work area of the form.*/
					    rc_intersect( &w.work, &rect ); 

					    /* The redraw is necessary to turn off the blinking cursor.
					     * We are going to need to send a redraw message to the calling
					     * cpx in case they have any custom redraws that need to be done.
					     */
					    Redraw_XForm_Do( &rect );
					    
					    if( msg[0] == WM_REDRAW )
					    {	
					       for( idx = 0; idx < 8; idx++ )
						   puntmsg[idx] = msg[idx];
					    }

					}
					/* Here we redraw/move the area that is dirtied */    
					do_windows( (int *)msg, (int *)&event );
					if( edit_obj )
					    MakeEditable( edit_obj );
					doedit = can_edit( tree, edit_obj );
					if( !doedit )
						cursor = FALSE;
					if( msg[0] == WM_REDRAW )
					{	
					   for( idx = 0; idx < 8; idx++ )
						   puntmsg[idx] = msg[idx];
					   return -1;
					}
				break;

				default:if( msg[0] == AC_CLOSE )
						SetAccCloseState( TRUE );
					if( msg[0] == AP_TERM )
					{
					    SetAccCloseState( TRUE );
					    msg[0] = AC_CLOSE;
					}
					if( msg[0] == WM_CLOSED )
					        SetWmCloseState( TRUE );
					for( idx = 0; idx < 8; idx++ )
						puntmsg[idx] = msg[idx];
					return -1;
			}
		}


/*
 * What about hot keys?? AIEEE!!
 */
		if( EvKey() ) {

			/*
			 * form_keybd() encapsulated here
			 */
			direction = NODIR;
			switch( key ) {

				case K_RETURN:
				case K_ENTER:
					next_obj = 0;
					direction = DEFAULTDIR;
					break;

				case K_BACKTAB:
				case K_UP:
					direction = BACKWARD;
					break;

				case K_TAB:
				case K_DOWN:
					direction = FORWARD;
					break;
			}

			if( direction != NODIR ) {
				key = 0;
				next_obj = find_obj( tree, edit_obj, direction );
				if( (direction == DEFAULTDIR) && (next_obj != 0) ) {
					Objc_change( tree, next_obj, &w.work,
 				        ObState(next_obj)|SELECTED, TRUE );
					cont = FALSE;
				}
			}
			/*
			 * End of form_keybd()
			 */

			/* The above code clears 'key', therefore, we'll
			 * check key FIRST, then test the ASCII and 
			 * scancode
			 */
			if( key && ( !( key & 0xff ) )  )
			{
			  if( ( key != K_UP     )  &&
			      ( key != K_DOWN   )  &&
			      ( key != K_RIGHT  )  &&
			      ( key != K_LEFT   )  &&
			      ( key != K_RETURN )  &&
			      ( key != K_ENTER  )  &&
			      ( key != K_TAB )	   &&
			      ( key != K_BACKTAB)
			    )
			    {
			      puntmsg[0] = CT_KEY;
			      puntmsg[3] = key;
			      return -1;
			    }  
			}

			if( key && doedit )
				objc_edit( tree, edit_obj, key, (int *)&idx, ED_CHAR );
		}

		if( EvButton() ) {
			next_obj = objc_find( tree, ROOT, MAX_DEPTH, m.x, m.y );
			if( next_obj == NIL ) {
				Bconout( 2, 7 );
				next_obj = 0;
			} else {
				cont = fm_button( tree, next_obj, clicks, &next_obj );
			}
		}

		if(  doedit && (!cont || (next_obj != 0)) && ( next_obj != edit_obj) )
		{
		   objc_edit( tree, edit_obj, 0, (int *)&idx, ED_END );
		   cursor = FALSE;
		}   		
	}

	return next_obj;
}
예제 #19
0
파일: scrolls.c 프로젝트: kioy/TA-Demo2
void
read_scroll(void)
{
    THING *obj;
    PLACE *pp;
    int y, x;
    int ch;
    int i;
    int discardit = FALSE;
    struct room *cur_room;
    THING *orig_obj;
    coord mp;

    obj = get_item("read", SCROLL);
    if (obj == NULL)
	return;
    if (obj->o_type != SCROLL)
    {
	if (!terse)
	    msg("there is nothing on it to read");
	else
	    msg("nothing to read");
	return;
    }
    /*
     * Calculate the effect it has on the poor guy.
     */
    if (obj == cur_weapon)
	cur_weapon = NULL;
    /*
     * Get rid of the thing
     */
    discardit = (obj->o_count == 1);
    leave_pack(obj, FALSE, FALSE);
    orig_obj = obj;

    switch (obj->o_which)
    {
	case S_CONFUSE:
	    /*
	     * Scroll of monster confusion.  Give him that power.
	     */
	    player.t_flags |= CANHUH;
	    msg("your hands begin to glow %s", pick_color("red"));
	when S_ARMOR:
	    if (cur_armor != NULL)
	    {
		cur_armor->o_arm--;
		cur_armor->o_flags &= ~ISCURSED;
		msg("your armor glows %s for a moment", pick_color("silver"));
	    }
	when S_HOLD:
	    /*
	     * Hold monster scroll.  Stop all monsters within two spaces
	     * from chasing after the hero.
	     */

	    ch = 0;
	    for (x = hero.x - 2; x <= hero.x + 2; x++)
		if (x >= 0 && x < NUMCOLS)
		    for (y = hero.y - 2; y <= hero.y + 2; y++)
			if (y >= 0 && y <= NUMLINES - 1)
			    if ((obj = moat(y, x)) != NULL && on(*obj, ISRUN))
			    {
				obj->t_flags &= ~ISRUN;
				obj->t_flags |= ISHELD;
				ch++;
			    }
	    if (ch)
	    {
		addmsg("the monster");
		if (ch > 1)
		    addmsg("s around you");
		addmsg(" freeze");
		if (ch == 1)
		    addmsg("s");
		endmsg();
		scr_info[S_HOLD].oi_know = TRUE;
	    }
	    else
		msg("you feel a strange sense of loss");
	when S_SLEEP:
	    /*
	     * Scroll which makes you fall asleep
	     */
	    scr_info[S_SLEEP].oi_know = TRUE;
	    no_command += rnd(SLEEPTIME) + 4;
	    player.t_flags &= ~ISRUN;
	    msg("you fall asleep");
	when S_CREATE:
	    /*
	     * Create a monster:
	     * First look in a circle around him, next try his room
	     * otherwise give up
	     */
	    i = 0;
	    for (y = hero.y - 1; y <= hero.y + 1; y++)
		for (x = hero.x - 1; x <= hero.x + 1; x++)
		    /*
		     * Don't put a monster in top of the player.
		     */
		    if (y == hero.y && x == hero.x)
			continue;
		    /*
		     * Or anything else nasty
		     * Also avoid a xeroc which is disguised as scroll
		     */
		    else if (moat(y, x) == NULL && step_ok(ch = winat(y, x)))
		    {
			if (ch == SCROLL
			    && find_obj(y, x)->o_which == S_SCARE)
				continue;
			else if (rnd(++i) == 0)
			{
			    mp.y = y;
			    mp.x = x;
			}
		    }
	    if (i == 0)
		msg("you hear a faint cry of anguish in the distance");
	    else
	    {
		obj = new_item();
		new_monster(obj, randmonster(FALSE), &mp);
	    }
	when S_ID_POTION:
	case S_ID_SCROLL:
	case S_ID_WEAPON:
	case S_ID_ARMOR:
	case S_ID_R_OR_S:
	{
	    int id_type[S_ID_R_OR_S + 1] =
		{ 0, 0, 0, 0, 0, POTION, SCROLL, WEAPON, ARMOR, R_OR_S };
	    /*
	     * Identify, let him figure something out
	     */
	    scr_info[obj->o_which].oi_know = TRUE;
	    msg("this scroll is an %s scroll", scr_info[obj->o_which].oi_name);
/*	    whatis(TRUE, id_type[obj->o_which]); */
	    if (idscr_md != TRUE)
		whatis(TRUE, id_type[obj->o_which]);
	    else
		whatis(FALSE, 0);
	}
	when S_MAP:
	    /*
	     * Scroll of magic mapping.
	     */
	    scr_info[S_MAP].oi_know = TRUE;
	    msg("oh, now this scroll has a map on it");
	    /*
	     * take all the things we want to keep hidden out of the window
	     */
	    for (y = 1; y < NUMLINES - 1; y++)
		for (x = 0; x < NUMCOLS; x++)
		{
		    pp = INDEX(y, x);
		    switch (ch = pp->p_ch)
		    {
			case DOOR:
			case STAIRS:
			    break;

			case '-':
			case '|':
			    if (!(pp->p_flags & F_REAL))
			    {
				ch = pp->p_ch = DOOR;
				pp->p_flags |= F_REAL;
			    }
			    break;

			case ' ':
			    if (pp->p_flags & F_REAL)
				goto def;
			    pp->p_flags |= F_REAL;
			    ch = pp->p_ch = PASSAGE;
			    /* FALLTHROUGH */

			case PASSAGE:
pass:
			    if (!(pp->p_flags & F_REAL))
				pp->p_ch = PASSAGE;
			    pp->p_flags |= (F_SEEN|F_REAL);
			    ch = PASSAGE;
			    break;

			case FLOOR:
			    if (pp->p_flags & F_REAL)
				ch = ' ';
			    else
			    {
				ch = TRAP;
				pp->p_ch = TRAP;
				pp->p_flags |= (F_SEEN|F_REAL);
			    }
			    break;

			default:
def:
			    if (pp->p_flags & F_PASS)
				goto pass;
			    ch = ' ';
			    break;
		    }
		    if (ch != ' ')
		    {
			if ((obj = pp->p_monst) != NULL)
			    obj->t_oldch = ch;
			if (obj == NULL || !on(player, SEEMONST))
			    mvaddch2(y, x, ch);
		    }
		}
	when S_FDET:
	    /*
	     * Potion of gold detection
	     */
	    ch = FALSE;
	    wclear(hw);
	    for (obj = lvl_obj; obj != NULL; obj = next(obj))
		if (obj->o_type == FOOD)
		{
		    ch = TRUE;
		    wmove(hw, obj->o_pos.y, obj->o_pos.x);
		    waddch2(hw, FOOD);
		}
	    if (ch)
	    {
		scr_info[S_FDET].oi_know = TRUE;
		show_win("Your nose tingles and you smell food.--More--");
	    }
	    else
		msg("your nose tingles");
	when S_TELEP:
	    /*
	     * Scroll of teleportation:
	     * Make him dissapear and reappear
	     */
	    {
		cur_room = proom;
		teleport();
		if (cur_room != proom)
		    scr_info[S_TELEP].oi_know = TRUE;
	    }
	when S_ENCH:
	    if (cur_weapon == NULL || cur_weapon->o_type != WEAPON)
		msg("you feel a strange sense of loss");
	    else
	    {
		cur_weapon->o_flags &= ~ISCURSED;
		if (rnd(2) == 0)
		    cur_weapon->o_hplus++;
		else
		    cur_weapon->o_dplus++;
		msg("your %s glows %s for a moment",
		    weap_info[cur_weapon->o_which].oi_name, pick_color("blue"));
	    }
	when S_SCARE:
	    /*
	     * Reading it is a mistake and produces laughter at her
	     * poor boo boo.
	     */
	    msg("you hear maniacal laughter in the distance");
	when S_REMOVE:
	    uncurse(cur_armor);
	    uncurse(cur_weapon);
	    uncurse(cur_ring[LEFT]);
	    uncurse(cur_ring[RIGHT]);
	    msg(choose_str("you feel in touch with the Universal Onenes",
			   "you feel as if somebody is watching over you"));
	when S_AGGR:
	    /*
	     * This scroll aggravates all the monsters on the current
	     * level and sets them running towards the hero
	     */
	    aggravate();
	    msg("you hear a high pitched humming noise");
	when S_PROTECT:
	    if (cur_armor != NULL)
	    {
		cur_armor->o_flags |= ISPROT;
		msg("your armor is covered by a shimmering %s shield",
		    pick_color("gold"));
	    }
	    else
		msg("you feel a strange sense of loss");
#ifdef MASTER
	otherwise:
	    msg("what a puzzling scroll!");
	    return;
#endif
    }
    obj = orig_obj;
    look(TRUE);	/* put the result of the scroll on the screen */
    status();

    call_it(&scr_info[obj->o_which]);

    if (discardit)
	discard(obj);
}
예제 #20
0
void
do_chase(struct thing *th, int flee)
{
    struct room    *rer;        /* room of chaser */
    struct room    *ree;        /* room of chasee */
    struct room    *old_room;   /* old room of monster */
    struct room    *new_room;   /* new room of monster */

    int i, mindist = INT_MAX, maxdist = INT_MIN, dist = INT_MIN;

    int last_door = -1;     /* Door we just came from */
    int stoprun = FALSE;    /* TRUE means we are there */
    int rundoor;            /* TRUE means run to a door */
    int hit_bad = FALSE;    /* TRUE means hit bad monster */
    int mon_attack;         /* TRUE means find a monster to hit */

    char    sch;
    struct linked_list *item;
    coord   this;           /* Temporary destination for chaser */

    if (!th->t_ischasing)
        return;

    /* Make sure the monster can move */

    if (th->t_no_move != 0)
    {
        th->t_no_move--;
        return;
    }

    /*
     * Bad monsters check for a good monster to hit, friendly monsters
     * check for a bad monster to hit.
     */

    mon_attack = FALSE;

    if (good_monster(*th))
    {
        hit_bad = TRUE;
        mon_attack = TRUE;
    }
    else if (on(*th, ISMEAN))
    {
        hit_bad = FALSE;
        mon_attack = TRUE;
    }

    if (mon_attack)
    {
        struct linked_list  *mon_to_hit;

	mon_to_hit = f_mons_a(th->t_pos.y, th->t_pos.x, hit_bad);

        if (mon_to_hit)
        {
            mon_mon_attack(th, mon_to_hit, pick_weap(th), NOTHROWN);
            return;
        }
    }
	
    /* no nearby monster to hit */
	
    rer = roomin(th->t_pos);            /* Find room of chaser */
    ree = roomin(th->t_chasee->t_pos);  /* Find room of chasee */

    /*
     * We don't count doors as inside rooms for this routine
     */

    if (mvwinch(stdscr, th->t_pos.y, th->t_pos.x) == DOOR)
        rer = NULL;

    this = th->t_chasee->t_pos;

    /*
     * If we are not in a corridor and not a phasing monster, then if we
     * are running after the player, we run to a door if he is not in the
     * same room. If we are fleeing, we run to a door if he IS in the
     * same room.  Note:  We don't bother with doors in mazes. Phasing 
     * monsters don't need to look for doors. There are no doors in mazes
     * and throne rooms. 
     */

    if (levtype != MAZELEV && levtype != THRONE && rer != NULL && off(*th, CANINWALL))
    {
        if (flee)
            rundoor = (rer == ree);
        else
            rundoor = (rer != ree);
    }
    else
        rundoor = FALSE;

    if (rundoor)
    {
        coord   d_exit;   /* A particular door */
        int exity, exitx;   /* Door's coordinates */

        if (th->t_doorgoal != -1)
        { /* Do we already have the goal? */
            this = rer->r_exit[th->t_doorgoal];
            dist = 0;   /* Indicate that we have our door */
        }
        else
            for (i = 0; i < rer->r_nexits; i++)
            {   /* Loop through doors */
                d_exit = rer->r_exit[i];
                exity = d_exit.y;
                exitx = d_exit.x;

                /* Avoid secret doors */
                if (mvwinch(stdscr, exity, exitx) == DOOR)
                {
                    /* Were we just on this door? */
                    if (ce(d_exit, th->t_oldpos))
                        last_door = i;
                    else
                    {
                        dist = DISTANCE(th->t_chasee->t_pos, d_exit);

                        /*
                         * If fleeing, we want to
                         * maximize distance from
                         * door to what we flee, and
                         * minimize distance from
                         * door to us.
                         */

                        if (flee)
                            dist-=DISTANCE(th->t_pos,d_exit);

                        /*
                         * Maximize distance if
                         * fleeing, otherwise
                         * minimize it
                         */

                        if ((flee && (dist > maxdist)) ||
                            (!flee && (dist < mindist)))
                        {
                            th->t_doorgoal = i; /* Use this door */
                            this = d_exit;
                            mindist = maxdist = dist;
                        }
                    }
                }
            }

        /* Could we not find a door? */
        if (dist == INT_MIN)
        {
            /* If we were on a door, go ahead and use it */
            if (last_door != -1)
            {
                th->t_doorgoal = last_door;
                this = th->t_oldpos;
                dist = 0;   /* Indicate that we found a door */
            }
        }

        /* Indicate that we do not want to flee from the door */
        if (dist != INT_MIN)
            flee = FALSE;
    }
    else
        th->t_doorgoal = -1;    /* Not going to any door */

    /*
     * this now contains what we want to run to this time so we run to
     * it.  If we hit it we either want to fight it or stop running
     */

    if (!chase(th, &this, flee))
    {
        if (ce(th->t_nxtpos, hero))
        {
            /* merchants try to sell something */

            if (on(*th, CANSELL))
            {
                sell(th);
                return;
            }
            else if (off(*th, ISFRIENDLY) && off(*th, ISCHARMED)
                    && (off(*th, CANFLY) || (on(*th, CANFLY) && rnd(2))))
                    attack(th, pick_weap(th), FALSE);
                return;
        }
        else if (on(*th, NOMOVE))
            stoprun = TRUE;
    }

    if (!curr_mons)
        return;     /* Did monster get itself killed? */

    if (on(*th, NOMOVE))
        return;

    /* If we have a scavenger, it can pick something up */

    if ((item = find_obj(th->t_nxtpos.y, th->t_nxtpos.x)) != NULL)
    {
		struct linked_list *node, *top = item;
        struct object *obt;
		
		while(top)
		{
			/* grab all objects that qualify */
			
			struct object *obj = OBJPTR(item);
			
			obt = OBJPTR(top);
			node = obt->next_obj;
			
			if (on(*th, ISSCAVENGE) ||
                ((on(*th, CANWIELD) || on(*th, CANSHOOT)) &&
                (obj->o_type == WEAPON || obj->o_type == ARMOR)) ||
                (on(*th, CANCAST) && is_magic(obj))) 
			{
                rem_obj(top, FALSE);
                attach(th->t_pack, top);
            }
			
			top = node;
		}
		
		light(&hero);
    }

    mvwaddch(cw, th->t_pos.y, th->t_pos.x, th->t_oldch);
    sch = CCHAR( mvwinch(cw, th->t_nxtpos.y, th->t_nxtpos.x) );

    /* Get old and new room of monster */
    old_room = roomin(th->t_pos);
    new_room = roomin(th->t_nxtpos);

    /* If the monster can illuminate rooms, check for a change */
    if (on(*th, HASFIRE))
    {
        /* Is monster entering a room? */
        if (old_room != new_room && new_room != NULL)
        {
            new_room->r_flags |= HASFIRE;
            new_room->r_fires++;
            if (cansee(th->t_nxtpos.y, th->t_nxtpos.x) && new_room->r_fires==1)
                light(&hero);
        }

        /* Is monster leaving a room? */
        if (old_room != new_room && old_room != NULL)
        {
            if (--(old_room->r_fires) <= 0)
            {
                old_room->r_flags &= ~HASFIRE;
                if (cansee(th->t_pos.y, th->t_pos.x))
                    light(&th->t_pos);
            }
        }
    }

    /*
     * If monster is entering player's room and player can see it, stop
     * the player's running.
     */

    if (new_room != old_room && new_room != NULL &&
        new_room == ree && cansee(th->t_nxtpos.y, th->t_nxtpos.x) &&
        (off(*th, ISINVIS) || (off(*th, ISSHADOW) || rnd(10) == 0) ||
         on(player, CANSEE)) && off(*th, CANSURPRISE))
        running = FALSE;

    if (rer != NULL && (rer->r_flags & ISDARK) &&
        !(rer->r_flags & HASFIRE) && sch == FLOOR &&
         DISTANCE(th->t_nxtpos, th->t_pos) < see_dist &&
        off(player, ISBLIND))
        th->t_oldch = ' ';
    else
        th->t_oldch = sch;

    if (cansee(th->t_nxtpos.y, th->t_nxtpos.x) &&
      off(*th, ISINWALL) &&
      ((off(*th, ISINVIS) && (off(*th, ISSHADOW) || rnd(100) < 10)) ||
      on(player, CANSEE)) &&
      off(*th, CANSURPRISE))
        mvwaddch(cw, th->t_nxtpos.y, th->t_nxtpos.x, th->t_type);

    mvwaddch(mw, th->t_pos.y, th->t_pos.x, ' ');
    mvwaddch(mw, th->t_nxtpos.y, th->t_nxtpos.x, th->t_type);

    /* Record monster's last position (if new one is different) */

    if (!ce(th->t_nxtpos, th->t_pos))
        th->t_oldpos = th->t_pos;

    th->t_pos = th->t_nxtpos; /* Mark the monster's new position */

    /* If the monster is on a trap, trap it */

    sch = CCHAR(mvinch(th->t_nxtpos.y, th->t_nxtpos.x));

    if (isatrap(sch))
    {
        debug("Monster trapped by %c.", sch);

        if (cansee(th->t_nxtpos.y, th->t_nxtpos.x))
            th->t_oldch = sch;

        be_trapped(th, th->t_nxtpos);
    }

    /* And stop running if need be */

    if (stoprun && ce(th->t_pos, th->t_chasee->t_pos))
    {
        th->t_ischasing = FALSE;
        turn_off(*th, ISRUN);
    }
}
예제 #21
0
int action(string arg)
{
        string keyword,verb,type,err_msg,check_ob,clan,*ally;
        object obj;
        int check_clan;


        verb = query_verb();
        keyword = env->query("action/"+verb+"/keyword");
        type = env->query("action/"+verb+"/type");
        err_msg = env->query("action/"+verb+"/err_msg");
        check_ob = env->query("action/"+verb+"/check_ob");
        check_clan = env->query("action/"+verb+"/check_clan");
        sscanf(base_name(env),"/open/clan/%s/%*s",clan);
        ally = CLAN_D->clan_query( this_player()->query("clan/id"), "ally" );

         if(!env->query("action/"+verb+"/filename")&& env->query("action/"+verb+"/filename")=="")
                return notify_fail("这个指令尚未完成。\n");
        if(!type) return notify_fail("这个指令尚未完成。\n");

// 这边是检查帮派的部份.
        switch(check_clan){
// 1时..就非本帮的不能使用...        
        case 1:
        if(this_player()->query("clan/id") != clan)
                return 0;
        break;
// 2.非同盟帮的不能使用.
        case 2:
        if(member_array( clan, ally ) == -1 && 
           this_player()->query("clan/id") != clan)
                return 0;
        default:
        }


        
        if(arg && keyword=="") return notify_fail(err_msg+"\n");  
        else if(keyword != "" && (!arg || arg != keyword)) return notify_fail(err_msg+"\n");
        if(check_ob && !obj=present(check_ob,this_player()))
                return notify_fail(err_msg+"\n");
        if(obj) destruct(obj);

        type(verb,"action");
return 1;
}

int type(string verb,string ftype)
{
        string type,filename,check;
        type = env->query(ftype+"/"+verb+"/type");
        filename  = env->query(ftype+"/"+verb+"/filename"); 
//下面是防作弊检查
// 只检查帮派的区域,帮派以外的区域不给inherit...
       if(filename!="" && sscanf(filename,"/open/clan/%s/%*s",check)!=2){
        log_file("clan/move_bug",sprintf("[%s] %s(%s)的房间 filename 为 %s\n",
            ctime(time()),
                        this_player()->name(),
                        getuid(this_player()),
filename,
        base_name(env)));
                return 0;
        }
// 以下是捡查该用那一种的移动,或招换..之类的..
// 并各自呼叫各字的fun...

        switch(type){

        case "action_move":
                action_move(ftype,verb);
        break;

        case "link_way":
                link_way(ftype,verb);
        break;

        case "add_mob":
                add_mob(ftype,verb);
        break;

        case "find_obj":
                find_obj(ftype,verb);
        break;

        }
        return 1;


}
예제 #22
0
/*
 * do_chase:
 *	Make one thing chase another.
 */
void
do_chase(struct thing *th, int flee)
{
    register struct room *rer, *ree,	/* room of chaser, room of chasee */
			*old_room,	/* old room of monster */
			*new_room;	/* new room of monster */
    register int mindist = MAXINT, maxdist = MININT, dist = MININT, i,
		 last_door = -1;	/* Door we just came from */
    register int stoprun = FALSE,	/* TRUE means we are there */
		  rundoor;		/* TRUE means run to a door */
	int mdead = 0;
    register int sch;
    coord this;				/* Temporary destination for chaser */

    /* Make sure the monster can move */
    if (th->t_no_move != 0) {
	th->t_no_move--;
	return;
    }

    rer = roomin(&th->t_pos);	/* Find room of chaser */
    ree = roomin(th->t_dest);	/* Find room of chasee */

    /*
     * We don't count doors as inside rooms for this routine
     */
    if (mvwinch(stdscr, th->t_pos.y, th->t_pos.x) == DOOR)
	rer = NULL;
    this = *th->t_dest;

    /*
     * If we are not in a corridor and not a Xorn, then if we are running
     * after the player, we run to a door if he is not in the same room.
     * If we are fleeing, we run to a door if he IS in the same room.
     * Note:  We don't bother with doors in mazes.
     */
    if (levtype != MAZELEV && rer != NULL && off(*th, CANINWALL)) {
	if (flee) rundoor = (rer == ree);
	else rundoor = (rer != ree);
    }
    else rundoor = FALSE;

    if (rundoor) {
	coord exit;	/* A particular door */
	int exity, exitx;	/* Door's coordinates */

	if (th->t_doorgoal != -1) {	/* Do we already have the goal? */
	    this = rer->r_exit[th->t_doorgoal];
	    dist = 0;	/* Indicate that we have our door */
	}

	else for (i = 0; i < rer->r_nexits; i++) {	/* Loop through doors */
	    exit = rer->r_exit[i];
	    exity = exit.y;
	    exitx = exit.x;

	    /* Avoid secret doors */
	    if (mvwinch(stdscr, exity, exitx) == DOOR) {
		/* Were we just on this door? */
		if (ce(exit, th->t_oldpos)) last_door = i;

		else {
		    dist = DISTANCE(th->t_dest->y, th->t_dest->x, exity, exitx);

		    /* If fleeing, we want to maximize distance from door to
		     * what we flee, and minimize distance from door to us.
		     */
		    if (flee)
		       dist -= DISTANCE(th->t_pos.y, th->t_pos.x, exity, exitx);

		    /* Maximize distance if fleeing, otherwise minimize it */
		    if ((flee && (dist > maxdist)) ||
			(!flee && (dist < mindist))) {
			th->t_doorgoal = i;	/* Use this door */
			this = exit;
			mindist = maxdist = dist;
		    }
		}
	    }
	}

	/* Could we not find a door? */
	if (dist == MININT) {
	    /* If we were on a door, go ahead and use it */
	    if (last_door != -1) {
		th->t_doorgoal = last_door;
		this = th->t_oldpos;
		dist = 0;	/* Indicate that we found a door */
	    }
	}

	/* Indicate that we do not want to flee from the door */
	if (dist != MININT) flee = FALSE;
    }

    else th->t_doorgoal = -1;	/* Not going to any door */
    /*
     * this now contains what we want to run to this time
     * so we run to it.  If we hit it we either want to fight it
     * or stop running
     */
    if (!chase(th, &this, flee, &mdead)) {
	if (ce(ch_ret, hero)) {
	    /* merchants try to sell something */
	    if (on(*th, CANSELL)) 
		sell(th);
	    else if (on(*th, ISCHARMED))
		{}				/* future enhancements */
	    else if (on(*th, ISFRIENDLY))
		{}
	    else
		attack(th, NULL, FALSE);
	    return;
	}
	else if (on(*th, NOMOVE))
	    stoprun = TRUE;
    }

    if (on(*th, ISDEAD))
		return;	/* Did monster get itself killed? */

    if (on(*th, NOMOVE)) 
	return;

    /* If we have a scavenger, it can pick something up */
    if (on(*th, ISSCAVENGE)) {
	register struct linked_list *item;

	if ((item = find_obj(ch_ret.y, ch_ret.x)) != NULL) {
	    register int floor = (roomin(&ch_ret) == NULL) ? PASSAGE : FLOOR;

	    detach(lvl_obj, item);
	    mvaddch(ch_ret.y, ch_ret.x, floor);
	    mvwaddch(cw, ch_ret.y, ch_ret.x, floor);
	    attach(th->t_pack, item);
	}
    }

    mvwaddch(cw, th->t_pos.y, th->t_pos.x, th->t_oldch);
    sch = CCHAR( mvwinch(cw, ch_ret.y, ch_ret.x) );

    /* Get old and new room of monster */
    old_room=roomin(&th->t_pos);
    new_room=roomin(&ch_ret);

    /* If the monster can illuminate rooms, check for a change */
    if (on(*th, HASFIRE)) {
	/* Is monster entering a room? */
	if (old_room != new_room && new_room != NULL) {
	    new_room->r_flags |= HASFIRE;
	    new_room->r_fires++;
	    if (cansee(ch_ret.y, ch_ret.x) && new_room->r_fires == 1)
		light(&hero);
	}

	/* Is monster leaving a room? */
	if (old_room != new_room && old_room != NULL) {
	    if (--(old_room->r_fires) <= 0) {
		old_room->r_flags &= ~HASFIRE;
		if (cansee(th->t_pos.y, th->t_pos.x)) light(&th->t_pos);
	    }
	}
    }

    /* If monster is entering player's room and player can see it,
     * stop the player's running.
     */
    if (new_room != old_room && new_room != NULL &&
	new_room == ree && cansee(unc(ch_ret)) &&
	(off(*th, ISINVIS) || (off(*th, ISSHADOW) || rnd(10) == 0) ||
	on(player, CANSEE)) && off(*th, CANSURPRISE))
		running = FALSE;

    if (rer != NULL && (rer->r_flags & ISDARK) && 
	!(rer->r_flags & HASFIRE) && sch == FLOOR &&
	DISTANCE(ch_ret.y, ch_ret.x, th->t_pos.y, th->t_pos.x) < see_dist &&
	off(player, ISBLIND))
	    th->t_oldch = ' ';
    else
	th->t_oldch = sch;

    if (cansee(unc(ch_ret)) &&
	off(*th, ISINWALL) &&
	((off(*th, ISINVIS) && (off(*th, ISSHADOW) || rnd(100) < 10)) ||
	 on(player, CANSEE)) &&
	off(*th, CANSURPRISE))
        mvwaddch(cw, ch_ret.y, ch_ret.x, th->t_type);
    mvwaddch(mw, th->t_pos.y, th->t_pos.x, ' ');
    mvwaddch(mw, ch_ret.y, ch_ret.x, th->t_type);

    /* Record monster's last position (if new one is different) */
    if (!ce(ch_ret, th->t_pos)) th->t_oldpos = th->t_pos;
    th->t_pos = ch_ret;		/* Mark the monster's new position */

    /* If the monster is on a trap, trap it */
    sch = CCHAR( mvinch(ch_ret.y, ch_ret.x) );
    if (isatrap(sch)) {
	debug("Monster trapped by %c.", sch);
	if (cansee(ch_ret.y, ch_ret.x)) th->t_oldch = sch;
	be_trapped(th, &ch_ret);
    }


    /*
     * And stop running if need be
     */
    if (stoprun && ce(th->t_pos, *(th->t_dest)))
	turn_off(*th, ISRUN);
}