Пример #1
0
/*
 * Return the salt size.
 * The size of the salt string is between 8 and 16 bytes for the SHA crypt
 * methods.
 */
static size_t SHA_salt_size (void)
{
	double rand_size;
	seedRNG ();
	rand_size = (double) 9.0 * random () / RAND_MAX;
	return (size_t) (8 + rand_size);
}
Пример #2
0
/*
 * Return a salt prefix specifying the rounds number for the SHA crypt methods.
 */
static /*@observer@*/const char *SHA_salt_rounds (/*@null@*/int *prefered_rounds)
{
	static char rounds_prefix[18];
	long rounds;

	if (NULL == prefered_rounds) {
		long min_rounds = getdef_long ("SHA_CRYPT_MIN_ROUNDS", -1);
		long max_rounds = getdef_long ("SHA_CRYPT_MAX_ROUNDS", -1);
		double rand_rounds;

		if ((-1 == min_rounds) && (-1 == max_rounds)) {
			return "";
		}

		if (-1 == min_rounds) {
			min_rounds = max_rounds;
		}

		if (-1 == max_rounds) {
			max_rounds = min_rounds;
		}

		if (min_rounds > max_rounds) {
			max_rounds = min_rounds;
		}

		seedRNG ();
		rand_rounds = (double) (max_rounds-min_rounds+1.0) * random ();
		rand_rounds /= RAND_MAX;
		rounds = min_rounds + rand_rounds;
	} else if (0 == *prefered_rounds) {
		return "";
	} else {
		rounds = *prefered_rounds;
	}

	/* Sanity checks. The libc should also check this, but this
	 * protects against a rounds_prefix overflow. */
	if (rounds < ROUNDS_MIN) {
		rounds = ROUNDS_MIN;
	}

	if (rounds > ROUNDS_MAX) {
		rounds = ROUNDS_MAX;
	}

	(void) snprintf (rounds_prefix, 18, "rounds=%ld$", rounds);

	/* Sanity checks. That should not be necessary. */
	rounds_prefix[17] = '\0';
	if ('$' != rounds_prefix[16]) {
		rounds_prefix[17] = '$';
	}

	return rounds_prefix;
}
/**
 * Calculate the multiple scattering correction factor and weight for the given
 * mur value
 * @param irp Index of current mur point (assumed zero based)
 * @param muR Single \f$\mu*r\f$ slice value
 * @param abs Absorption and self-attenuation factor (\f$A_s\f$ in Mayers paper)
 * @return A pair of (factor,weight)
 */
std::pair<double, double>
MayersSampleCorrectionStrategy::calculateMS(const size_t irp, const double muR,
                                            const double abs) {
  // Radial coordinate raised to power 1/3 to ensure uniform density of points
  // across circle following discussion with W.G.Marshall (ISIS)
  const double radDistPower = 1. / 3.;
  const double muH = muR * (m_pars.cylHeight / m_pars.cylRadius);
  const double cosaz = cos(m_pars.azimuth);
  seedRNG(irp);

  // Take an average over a number of sets of second scatters
  std::vector<double> deltas(m_pars.msNRuns, 0.0);
  for (size_t j = 0; j < m_pars.msNRuns; ++j) {
    double sum = 0.0;
    for (size_t i = 0; i < m_pars.msNEvents; ++i) {
      // Random (r,theta,z)
      const double r1 = pow(m_rng->nextValue(), radDistPower) * muR;
      const double r2 = pow(m_rng->nextValue(), radDistPower) * muR;
      const double z1 = m_rng->nextValue() * muH;
      const double z2 = m_rng->nextValue() * muH;
      const double th1 = m_rng->nextValue() * TWOPI;
      const double th2 = m_rng->nextValue() * TWOPI;
      double fact1 = pow(muR, 2) - std::pow(r1 * sin(th1), 2);
      if (fact1 < 0.0)
        fact1 = 0.0;
      // Path into first point
      const double mul1 = sqrt(fact1) + r1 * cos(th1);
      double fact2 = pow(muR, 2) - pow(r2 * sin(m_pars.twoTheta - th2), 2);
      if (fact2 < 0.0)
        fact2 = 0.0;
      // Path out from final point
      const double mul2 =
          (sqrt(fact2) - r2 * cos(m_pars.twoTheta - th2)) / cosaz;
      // Path between point 1 & 2
      const double mul12 =
          sqrt(pow(r1 * cos(th1) - r2 * cos(th2), 2) +
               pow(r1 * sin(th1) - r2 * sin(th2), 2) + pow(z1 - z2, 2));
      if (mul12 < 0.01)
        continue;
      sum += exp(-(mul1 + mul2 + mul12)) / pow(mul12, 2);
    }
    const double beta =
        pow(M_PI * muR * muR * muH, 2) * sum / to<double>(m_pars.msNEvents);
    const double delta = 0.25 * beta / (M_PI * abs * muH);
    deltas[j] = delta;
  }
  auto stats =
      getStatistics(deltas, StatOptions::Mean | StatOptions::CorrectedStdDev);
  return std::make_pair(stats.mean, stats.mean / stats.standard_deviation);
}
Пример #4
0
/*
 * Return a salt prefix specifying the rounds number for the SHA crypt methods.
 */
static /*@observer@*/const char *SHA_salt_rounds (/*@null@*/int *prefered_rounds)
{
	static char rounds_prefix[18]; /* Max size: rounds=999999999$ */
	long rounds;

	if (NULL == prefered_rounds) {
		double rand_rounds;

		if ((-1 == sha_crypt_min_rounds) && (-1 == sha_crypt_max_rounds)) {
			return "";
		}

		if (-1 == sha_crypt_min_rounds) {
			sha_crypt_min_rounds = sha_crypt_max_rounds;
		}

		if (-1 == sha_crypt_max_rounds) {
			sha_crypt_max_rounds = sha_crypt_min_rounds;
		}

		if (sha_crypt_min_rounds > sha_crypt_max_rounds) {
			sha_crypt_max_rounds = sha_crypt_min_rounds;
		}

		seedRNG ();
		rand_rounds = (double) (sha_crypt_max_rounds-sha_crypt_min_rounds+1.0) * random ();
		rand_rounds /= RAND_MAX;
		rounds = sha_crypt_min_rounds + rand_rounds;
	} else if (0 == *prefered_rounds) {
		return "";
	} else {
		rounds = *prefered_rounds;
	}

	/* Sanity checks. The libc should also check this, but this
	 * protects against a rounds_prefix overflow. */
	if (rounds < ROUNDS_MIN) {
		rounds = ROUNDS_MIN;
	}

	if (rounds > ROUNDS_MAX) {
		rounds = ROUNDS_MAX;
	}

	(void) snprintf (rounds_prefix, sizeof rounds_prefix,
	                 "rounds=%ld$", rounds);

	return rounds_prefix;
}
Пример #5
0
static /*@observer@*/const char *gensalt (size_t salt_size)
{
	static char salt[32];

	salt[0] = '\0';

	assert (salt_size >= MIN_SALT_SIZE &&
	        salt_size <= MAX_SALT_SIZE);
	seedRNG ();
	strcat (salt, l64a (random()));
	do {
		strcat (salt, l64a (random()));
	} while (strlen (salt) < salt_size);

	salt[salt_size] = '\0';

	return salt;
}
Пример #6
0
MapGenerator::TerrainBlock MapGenerator::getBlock(std::int64_t row,
                                                  std::int64_t col) const {
   MapGenerator::TerrainBlock terrainBlock;

   // We need size^2 gradient vectors.
   constexpr std::size_t size = blockSize / gridSize + 1;

   // Assign a random gradient vector of unit length to each grid node.  TODO: we really
   // only need to store (size + 2) vectors at a time.
   std::array<std::array<std::array<float, 2>, size>, size> gradients;
   {
      // Use the gradient vectors of adjacent blocks for two edges.  Otherwise we would
      // get visible transitions at block edges, since adjacent tiles would use different
      // gradient vectors.
      std::size_t i = size - 1;
      std::size_t j = 0;

      // Seed of the adjacent block to the bottom.
      seedRNG(row + 1, col);
      // Get the random gradients used for the top row of the block to the bottom.  Use
      // them for this bottom row.
      for (; j < size - 1; ++j) {
         gradients[i][j] = getGradient();
      }

      // Seed of the adjacent block to the bottom-right.
      seedRNG(row + 1, col + 1);
      assert(j == size - 1);
      gradients[i][j] = getGradient();

      // Seed of the adjacent block to the right.
      seedRNG(row, col + 1);
      i = 0;
      assert(j == size - 1);
      gradients[i][j] = getGradient();
      // Throw the remaining (size - 2) pairs of random numbers for the top row away.
      rNGen.discard(2 * size - 4);
      // The next random numbers are those the block to the right uses for its leftmost
      // column.  Use them for the rightmost column.
      for (++i; i < size - 1; ++i) {
         gradients[i][j] = getGradient();
      }
   }
   // Finally, use the seed of this block.
   seedRNG(row, col);
   // The gradient vectors for the top row and leftmost column are the ones adjacent
   // blocks also use.  They are computed first.  Otherwise we would have to waste more
   // time generating and throwing away random numbers in the code generating gradients of
   // other blocks above.
   for (std::size_t j = 0; j < size - 1; ++j) {
      gradients[0][j] = getGradient();
   }
   for (std::size_t j = 0; j < size - 1; ++j) {
      for (std::size_t i = 1; i < size - 1; ++i) {
         gradients[i][j] = getGradient();
      }
   }

#ifdef DEBUG  // Assert all the gradients are unit vectors. {{{1
   {
      constexpr float epsilon = 0.01f;
      for (std::size_t i = 0; i < size; ++i) {
         for (std::size_t j = 0; j < size; ++j) {
            auto& gradient = gradients[i][j];
            assert(dotProduct(gradient, gradient) <= 1.f + epsilon);
         }
      }
   }
#endif  // }}}1

   for (std::size_t i = 0; i < blockSize; ++i) {
      for (std::size_t j = 0; j < blockSize; ++j) {
         // Convert the indices to floats in the gradient grid.
         std::array<float, 2> point{static_cast<float>(j) / gridSize,
                                    static_cast<float>(i) / gridSize};
         // Determine into which grid cell (i, j) falls; store the cell's top-left corner
         // which is also the index of that point's gradient vector.  TODO: we could
         // iterate over grid cells and avoid repeating this computation.
         std::array<std::size_t, 2> topLeft{j / gridSize, i / gridSize};

#ifdef DEBUG  // Assert use of topLeft to index gradients is correct. {{{1
         assert(topLeft[0] + 1 < gradients.size());
         assert(topLeft[1] + 1 < gradients[0].size());
#endif  // }}}1

         // For each corner of that cell, determine the distance vector from the corner to
         // the point.
         std::array<std::array<float, 2>, 4> distance;
         distance[0] = {point[0] - topLeft[0], point[1] - topLeft[1]};
         distance[1] = {distance[0][0] - 1.f, distance[0][1]};
         distance[2] = {distance[0][0], distance[0][1] - 1.f};
         distance[3] = {distance[1][0], distance[2][1]};

#ifdef DEBUG  // Validate value of distance[0]. {{{1
         assert(0.f <= distance[0][0] && distance[0][0] <= 1.f);
         assert(0.f <= distance[0][1] && distance[0][1] <= 1.f);
#endif  // }}}1

         // For each of the 4 distance vectors, compute the dot product between it and the
         // corner's gradient vector.
         std::array<float, 4> dots{
             dotProduct(distance[0], gradients[topLeft[1]][topLeft[0]]),
             dotProduct(distance[1], gradients[topLeft[1]][topLeft[0] + 1]),
             dotProduct(distance[2], gradients[topLeft[1] + 1][topLeft[0]]),
             dotProduct(distance[3], gradients[topLeft[1] + 1][topLeft[0] + 1])};

#ifdef DEBUG  // ... {{{1
         {
            constexpr float epsilon = 0.01f;
            constexpr float maxDist = 1.414213562373 + epsilon;
            for (std::size_t n = 0; n < 4; ++n) {
               assert(dots[n] <= maxDist);
            }
         }
#endif  // }}}1

         // Interpolate between the 4 dot products.
         float xWeight = point[0] - topLeft[0];
         float yWeight = point[1] - topLeft[1];
         float topXAverage = lerp(dots[0], dots[1], xWeight);
         float bottomXAverage = lerp(dots[2], dots[3], xWeight);
         float value = lerp(topXAverage, bottomXAverage, yWeight);

         // constexpr float maxVal = std::sqrt(2) / 2;
         // assert(-maxVal <= value && value <= maxVal);
         // value += maxVal;      // Transform value into the range [0, 2 * maxValue].
         // value /= 2 * maxVal;  // Transform it into the range [0, 1].

         // I think my implementation of Perlin noise can result in values in the range
         // [-maxVal, maxVal].  However, the vast majority of values are much closer to
         // zero, so the commented out code above doesn't work very well.

         // This should kind of move most values into the range [-2.5, 2.5].
         value *= 5.f;
         // Now most should be in the range [0, 5].
         value += 2.5f;
         // Treat everything negative as 0 and everything bigger than or equal to 6 as 5.
         if (value < 0.f) value = 0.f;
         if (value >= 6.f) value = 5.f;
         // Now we only have values in [0, 6).  They can be converted to TileType values
         // by truncating.
         terrainBlock[i][j] = static_cast<TileType>(value);
      }
   }
   return terrainBlock;
}