Esempio n. 1
0
bool move_unit(unit *new_pool, unit *to_move)
{
	if (new_pool != NULL)
	{
		append_unit(new_pool, remove_unit(to_move));
	}
	else
	{
		new_pool = remove_unit(to_move);
	}

	return(true);
}
Esempio n. 2
0
static int yp_int_to_bin(
	TXT_BIN_PARAMS,
	int64_t min,
	int64_t max,
	uint8_t min_bytes,
	yp_style_t style)
{
	char *end = (char *)txt;

	int64_t number = strtoll(txt, &end, 10);

	// Check if the whole string is invalid.
	if (end == txt) {
		return KNOT_EINVAL;
	}

	// Check the rest of the string for a unit.
	if (*end != '\0') {
		// Check just for one-char rest.
		if (*(end + 1) != '\0') {
			return KNOT_EINVAL;
		}

		// Try to apply the unit on the number.
		if (remove_unit(&number, *end, style) != KNOT_EOK) {
			return KNOT_EINVAL;
		}
	}

	if (number < min || number > max) {
		return KNOT_ERANGE;
	}

	// Convert the number to litte-endian byte order.
	number = htole64(number);

	// Store the result
	memcpy(bin, &number, sizeof(number));
	*bin_len = sizeof(number);

	// Ignore trailing zeroes.
	for (int i = 7; i >= min_bytes; i--) {
		if (((uint8_t *)&number)[i] != 0) {
			break;
		}
		(*bin_len)--;
	}

	return KNOT_EOK;
}
Esempio n. 3
0
void remove_region(region ** rlist, region * r)
{

    while (r->units) {
        unit *u = r->units;
        i_freeall(&u->items);
        remove_unit(&r->units, u);
    }

    runhash(r);
    unhash_uid(r);
    while (*rlist && *rlist != r)
        rlist = &(*rlist)->next;
    assert(*rlist == r);
    *rlist = r->next;
    r->next = deleted_regions;
    deleted_regions = r;
}
Esempio n. 4
0
void chaos(region * r)
{
  if (rng_int() % 100 < 8) {
    switch (rng_int() % 3) {
      case 0:                  /* Untote */
        if (!fval(r->terrain, SEA_REGION)) {
          unit *u = random_unit(r);
          if (u && playerrace(u_race(u))) {
            ADDMSG(&u->faction->msgs, msg_message("chaos_disease", "unit", u));
            u_setfaction(u, get_monsters());
            u_setrace(u, get_race(RC_GHOUL));
          }
        }
        break;
      case 1:                  /* Drachen */
        if (random_unit(r)) {
          int mfac = 0;
          unit *u;
          switch (rng_int() % 3) {
            case 0:
              mfac = 100;
              u =
                createunit(r, get_monsters(), rng_int() % 8 + 1,
                get_race(RC_FIREDRAGON));
              break;
            case 1:
              mfac = 500;
              u =
                createunit(r, get_monsters(), rng_int() % 4 + 1,
                get_race(RC_DRAGON));
              break;
            default:
              mfac = 1000;
              u =
                createunit(r, get_monsters(), rng_int() % 2 + 1,
                get_race(RC_WYRM));
              break;
          }
          if (mfac)
            set_money(u, u->number * (rng_int() % mfac));
          fset(u, UFL_ISNEW | UFL_MOVED);
        }
      case 2:                  /* Terrainveränderung */
        if (!fval(r->terrain, FORBIDDEN_REGION)) {
          if (!fval(r->terrain, SEA_REGION)) {
            direction_t dir;
            for (dir = 0; dir != MAXDIRECTIONS; ++dir) {
              region *rn = rconnect(r, dir);
              if (rn && fval(rn->terrain, SEA_REGION))
                break;
            }
            if (dir != MAXDIRECTIONS) {
              ship *sh = r->ships;
              unit **up;

              while (sh) {
                ship *nsh = sh->next;
                float dmg =
                  get_param_flt(global.parameters, "rules.ship.damage.atlantis",
                  0.50);
                damage_ship(sh, dmg);
                if (sh->damage >= sh->size * DAMAGE_SCALE) {
                  remove_ship(&sh->region->ships, sh);
                }
                sh = nsh;
              }

              for (up = &r->units; *up;) {
                unit *u = *up;
                if (u_race(u) != get_race(RC_SPELL) && u->ship == 0 && !canfly(u)) {
                  ADDMSG(&u->faction->msgs, msg_message("tidalwave_kill",
                      "region unit", r, u));
                  remove_unit(up, u);
                }
                if (*up == u)
                  up = &u->next;
              }
              ADDMSG(&r->msgs, msg_message("tidalwave", "region", r));

              while (r->buildings) {
                remove_building(&r->buildings, r->buildings);
              }
              terraform_region(r, newterrain(T_OCEAN));
            }
          } else {
            direction_t dir;
            for (dir = 0; dir != MAXDIRECTIONS; ++dir) {
              region *rn = rconnect(r, dir);
              if (rn && fval(rn->terrain, SEA_REGION))
                break;
            }
            if (dir != MAXDIRECTIONS) {
              terraform_region(r, chaosterrain());
            }
          }
        }
    }
  }
}
Esempio n. 5
0
/**
 * @ingroup COND
 * @brief   Wait on the condition.
 *
 * The ULT calling \c ABT_cond_timedwait() waits on the condition variable
 * until it is signaled or the absolute time specified by \c abstime passes.
 * If system time equals or exceeds \c abstime before \c cond is signaled,
 * the error code \c ABT_ERR_COND_TIMEDOUT is returned.
 *
 * The user should call this routine while the mutex specified as \c mutex is
 * locked. The mutex will be automatically released while waiting. After signal
 * is received and the waiting ULT is awakened, the mutex will be
 * automatically locked for use by the ULT. The user is then responsible for
 * unlocking mutex when the ULT is finished with it.
 *
 * @param[in] cond     handle to the condition variable
 * @param[in] mutex    handle to the mutex
 * @param[in] abstime  absolute time for timeout
 * @return Error code
 * @retval ABT_SUCCESS            on success
 * @retval ABT_ERR_COND_TIMEDOUT  timeout
 */
int ABT_cond_timedwait(ABT_cond cond, ABT_mutex mutex,
                       const struct timespec *abstime)
{
    int abt_errno = ABT_SUCCESS;
    ABTI_cond *p_cond = ABTI_cond_get_ptr(cond);
    ABTI_CHECK_NULL_COND_PTR(p_cond);
    ABTI_mutex *p_mutex = ABTI_mutex_get_ptr(mutex);
    ABTI_CHECK_NULL_MUTEX_PTR(p_mutex);

    double tar_time = convert_timespec_to_sec(abstime);

    ABTI_unit *p_unit;
    volatile int ext_signal = 0;

    p_unit = (ABTI_unit *)ABTU_calloc(1, sizeof(ABTI_unit));
    p_unit->pool = (ABT_pool)&ext_signal;
    p_unit->type = ABT_UNIT_TYPE_EXT;

    ABTI_mutex_spinlock(&p_cond->mutex);

    if (p_cond->p_waiter_mutex == NULL) {
        p_cond->p_waiter_mutex = p_mutex;
    } else {
        ABT_bool result = ABTI_mutex_equal(p_cond->p_waiter_mutex, p_mutex);
        if (result == ABT_FALSE) {
            ABTI_mutex_unlock(&p_cond->mutex);
            abt_errno = ABT_ERR_INV_MUTEX;
            goto fn_fail;
        }
    }

    if (p_cond->num_waiters == 0) {
        p_unit->p_prev = p_unit;
        p_unit->p_next = p_unit;
        p_cond->p_head = p_unit;
        p_cond->p_tail = p_unit;
    } else {
        p_cond->p_tail->p_next = p_unit;
        p_cond->p_head->p_prev = p_unit;
        p_unit->p_prev = p_cond->p_tail;
        p_unit->p_next = p_cond->p_head;
        p_cond->p_tail = p_unit;
    }

    p_cond->num_waiters++;

    ABTI_mutex_unlock(&p_cond->mutex);

    /* Unlock the mutex that the calling ULT is holding */
    ABTI_mutex_unlock(p_mutex);

    while (!ext_signal) {
        double cur_time = get_cur_time();
        if (cur_time >= tar_time) {
            remove_unit(p_cond, p_unit);
            abt_errno = ABT_ERR_COND_TIMEDOUT;
            break;
        }
        ABT_thread_yield();
    }
    ABTU_free(p_unit);

    /* Lock the mutex again */
    ABTI_mutex_spinlock(p_mutex);

  fn_exit:
    return abt_errno;

  fn_fail:
    HANDLE_ERROR_FUNC_WITH_CODE(abt_errno);
    goto fn_exit;
}