// Licensed to the Apache Software Foundation (ASF) under one
// or more contributor license agreements.  See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership.  The ASF licenses this file
// to you under the Apache License, Version 2.0 (the
// "License"); you may not use this file except in compliance
// with the License.  You may obtain a copy of the License at
//
//   http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing,
// software distributed under the License is distributed on an
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
// KIND, either express or implied.  See the License for the
// specific language governing permissions and limitations
// under the License.

#include "kudu/util/random_util.h"

#include <cstdint>
#include <cstring>
#include <limits>
#include <ostream>
#include <unordered_set>
#include <vector>

#include <glog/logging.h>
#include <gtest/gtest.h>

#include "kudu/gutil/map-util.h"
#include "kudu/util/int128.h"
#include "kudu/util/int128_util.h"
#include "kudu/util/random.h"
#include "kudu/util/test_util.h"

using std::unordered_set;

namespace kudu {

class RandomUtilTest : public KuduTest {
 protected:
  RandomUtilTest() : rng_(SeedRandom()) {}

  Random rng_;

  static const int kLenMax = 100;
  static const int kNumTrials = 100;
};

namespace {

// Checks string defined at start is set to \0 everywhere but [from, to)
void CheckEmpty(char* start, int from, int to, int stop) {
  DCHECK_LE(0, from);
  DCHECK_LE(from, to);
  DCHECK_LE(to, stop);
  for (int j = 0; (j == from ? j = to : j) < stop; ++j) {
    CHECK_EQ(start[j], '\0') << "Index " << j << " not null after defining"
                             << "indices [" << from << "," << to << ") of "
                             << "a nulled string [0," << stop << ").";
  }
}

} // anonymous namespace

// Makes sure that RandomString only writes the specified amount
TEST_F(RandomUtilTest, TestRandomString) {
  char start[kLenMax];

  for (int i = 0; i < kNumTrials; ++i) {
    memset(start, '\0', kLenMax);
    int to = rng_.Uniform(kLenMax + 1);
    int from = rng_.Uniform(to + 1);
    RandomString(start + from, to - from, &rng_);
    CheckEmpty(start, from, to, kLenMax);
  }

  // Corner case
  memset(start, '\0', kLenMax);
  RandomString(start, 0, &rng_);
  CheckEmpty(start, 0, 0, kLenMax);
}

// Static helper function for testing generation of random numbers in range.
// CreateRandomUniqueIntegers() doesn't support 128-bit integers yet. Hence a separate
// template function instead of member of TemplateRandomUtilTest class.
// TODO(bankim): Once CreateRandomIntegersInRange() supports 128-bit integers make it a
//               member function of TemplateRandomUtilTest class.
template <typename IntType>
static void RunCreateRandomIntegersInRangerHelper(int num_trials, IntType min_val, IntType max_val,
                                                  Random* rng) {
  static constexpr int kMaxNumVals = 1000;
  for (int i = 0; i < num_trials; ++i) {
    int num_vals = rng->Uniform(kMaxNumVals);
    auto vals = CreateRandomIntegersInRange<IntType>(num_vals, min_val, max_val, rng);
    ASSERT_EQ(num_vals, vals.size());
    for (const auto& v : vals) {
      ASSERT_GE(v, min_val);
      ASSERT_LT(v, max_val);
    }
  }
}

template<typename IntType>
class TemplateRandomUtilTest : public RandomUtilTest {
 public:
  void RunCreateRandomUniqueIntegers() {
    static constexpr int kMaxNumVals = 1000;
    for (int i = 0; i < kNumTrials; ++i) {
      unordered_set<IntType> avoid;
      for (int j = 0; j < i; ++j) {
        avoid.insert(j);
      }
      int num_vals = rng_.Uniform(kMaxNumVals);
      auto vals = CreateRandomUniqueIntegers<IntType>(num_vals, avoid, &rng_);
      ASSERT_EQ(num_vals, vals.size());
      for (const auto& v : vals) {
        ASSERT_FALSE(ContainsKey(avoid, v));
      }
    }
  }

  void RunCreateRandomIntegersInRange() {
    static constexpr IntType min_val = std::numeric_limits<IntType>::min();
    static constexpr IntType max_val = std::numeric_limits<IntType>::max();
    // Exercise entire range.
    RunCreateRandomIntegersInRangerHelper(kNumTrials, min_val, max_val, &rng_);
    // Exercise partial range.
    RunCreateRandomIntegersInRangerHelper(kNumTrials, min_val / 2, max_val / 2, &rng_);
  }
};

// Testing with char, short data-types will result in compile-time error, as expected.
// Hence no run-time unit tests for non-32/64-bit integers.
typedef ::testing::Types<int32_t, uint32_t, int64_t, uint64_t> IntTypes;
TYPED_TEST_SUITE(TemplateRandomUtilTest, IntTypes);

TYPED_TEST(TemplateRandomUtilTest, RunCreateRandomUniqueIntegers) {
  this->RunCreateRandomUniqueIntegers();
}

TYPED_TEST(TemplateRandomUtilTest, RunCreateRandomIntegersInRange) {
  this->RunCreateRandomIntegersInRange();
}

// TODO(bankim): CreateRandomUniqueIntegers() doesn't support 128-bit integers yet.
//               Once it does add int128_t and uint128_t types to IntTypes and use
//               templatized TemplateRandomUtilTest instead.
TEST_F(RandomUtilTest, RunCreateRandom128BitIntegersInRange) {
  // Exercise entire range.
  RunCreateRandomIntegersInRangerHelper<int128_t>(kNumTrials, INT128_MIN, INT128_MAX, &rng_);
  RunCreateRandomIntegersInRangerHelper<uint128_t>(kNumTrials, 0, UINT128_MAX, &rng_);

  // Exercise partial range.
  RunCreateRandomIntegersInRangerHelper<int128_t>(kNumTrials, INT128_MIN / 2, INT128_MAX / 2,
                                                  &rng_);
  RunCreateRandomIntegersInRangerHelper<uint128_t>(kNumTrials, 0, UINT128_MAX / 2, &rng_);
}

} // namespace kudu
