// Copyright 2015 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <algorithm>

#include "base/macros.h"
#include "net/cert/internal/extended_key_usage.h"
#include "net/der/input.h"
#include "testing/gtest/include/gtest/gtest.h"

namespace net {

namespace {

// Helper method to check if an EKU is present in a std::vector of EKUs.
bool HasEKU(const std::vector<der::Input>& list, const der::Input& eku) {
  for (const auto& oid : list) {
    if (oid == eku)
      return true;
  }
  return false;
}

// Check that we can read multiple EKUs from an extension.
TEST(ExtendedKeyUsageTest, ParseEKUExtension) {
  // clang-format off
  const uint8_t raw_extension_value[] = {
      0x30, 0x14,  // SEQUENCE (20 bytes)
      0x06, 0x08,  // OBJECT IDENTIFIER (8 bytes)
      0x2B, 0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x01,  // 1.3.6.1.5.5.7.3.1
      0x06, 0x08,  // OBJECT IDENTIFIER (8 bytes)
      0x2B, 0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x02  // 1.3.6.1.5.5.7.3.2
      // end of SEQUENCE
  };
  // clang-format on
  der::Input extension_value(raw_extension_value);

  std::vector<der::Input> ekus;
  EXPECT_TRUE(ParseEKUExtension(extension_value, &ekus));

  EXPECT_EQ(2u, ekus.size());
  EXPECT_TRUE(HasEKU(ekus, ServerAuth()));
  EXPECT_TRUE(HasEKU(ekus, ClientAuth()));
}

// Check that an extension with the same OID present multiple times doesn't
// cause an error.
TEST(ExtendedKeyUsageTest, RepeatedOid) {
  // clang-format off
  const uint8_t extension_bytes[] = {
      0x30, 0x14,  // SEQUENCE (20 bytes)
      0x06, 0x08,  // OBJECT IDENTIFIER (8 bytes)
      0x2B, 0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x01,  // 1.3.6.1.5.5.7.3.1
      0x06, 0x08,  // OBJECT IDENTIFIER (8 bytes)
      0x2B, 0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x01  // 1.3.6.1.5.5.7.3.1
  };
  // clang-format on
  der::Input extension(extension_bytes);

  std::vector<der::Input> ekus;
  EXPECT_TRUE(ParseEKUExtension(extension, &ekus));
  EXPECT_EQ(2u, ekus.size());
  for (const auto& eku : ekus) {
    EXPECT_EQ(ServerAuth(), eku);
  }
}

// Check that parsing an EKU extension which contains a private OID doesn't
// cause an error.
TEST(ExtendedKeyUsageTest, ParseEKUExtensionGracefullyHandlesPrivateOids) {
  // clang-format off
  const uint8_t extension_bytes[] = {
    0x30, 0x13,  // SEQUENCE (19 bytes)
    0x06, 0x08,  // OBJECT IDENTIFIER (8 bytes)
    0x2B, 0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x01,  // 1.3.6.1.5.5.7.3.1
    0x06, 0x07,  // OBJECT IDENTIFIER (7 bytes)
    0x2B, 0x06, 0x01, 0x04, 0x01, 0xD6, 0x79  // 1.3.6.1.4.1.11129
  };
  // clang-format on
  der::Input extension(extension_bytes);

  std::vector<der::Input> ekus;
  EXPECT_TRUE(ParseEKUExtension(extension, &ekus));
  EXPECT_EQ(2u, ekus.size());
  EXPECT_TRUE(HasEKU(ekus, ServerAuth()));

  const uint8_t google_oid[] = {0x2B, 0x06, 0x01, 0x04, 0x01, 0xD6, 0x79};
  der::Input google(google_oid);
  EXPECT_TRUE(HasEKU(ekus, google));
}

// Test a variety of bad inputs.

// If the extension value has data following the sequence of oids, parsing it
// should fail.
TEST(ExtendedKeyUsageTest, ExtraData) {
  // clang-format off
  const uint8_t extra_data[] = {
      0x30, 0x14,  // SEQUENCE (20 bytes)
      0x06, 0x08,  // OBJECT IDENTIFIER (8 bytes)
      0x2B, 0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x01,  // 1.3.6.1.5.5.7.3.1
      0x06, 0x08,  // OBJECT IDENTIFIER (8 bytes)
      0x2B, 0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x02,  // 1.3.6.1.5.5.7.3.2
      // end of SEQUENCE
      0x02, 0x01,  // INTEGER (1 byte)
      0x01  // 1
  };
  // clang-format on

  std::vector<der::Input> ekus;
  EXPECT_FALSE(ParseEKUExtension(der::Input(extra_data), &ekus));
}

// Check that ParseEKUExtension only accepts a sequence containing only oids.
// This test case has an integer in the sequence (which should fail). A key
// difference between this test case and ExtendedKeyUsageTest.ExtraData is where
// the sequence ends - in this test case the integer is still part of the
// sequence, while in ExtendedKeyUsageTest.ExtraData the integer is after the
// sequence.
TEST(ExtendedKeyUsageTest, NotAnOid) {
  // clang-format off
  const uint8_t not_an_oid[] = {
      0x30, 0x0d,  // SEQUENCE (13 bytes)
      0x06, 0x08,  // OBJECT IDENTIFIER (8 bytes)
      0x2B, 0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x01,  // 1.3.6.1.5.5.7.3.1
      0x02, 0x01,  // INTEGER (1 byte)
      0x01  // 1
      // end of SEQUENCE
  };
  // clang-format on

  std::vector<der::Input> ekus;
  EXPECT_FALSE(ParseEKUExtension(der::Input(not_an_oid), &ekus));
}

// Checks that the list of oids passed to ParseEKUExtension are in a sequence,
// instead of one or more oid tag-length-values concatenated together.
TEST(ExtendedKeyUsageTest, NotASequence) {
  // clang-format off
  const uint8_t not_a_sequence[] = {
      0x06, 0x08,  // OBJECT IDENTIFIER (8 bytes)
      0x2B, 0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x01  // 1.3.6.1.5.5.7.3.1
  };
  // clang-format on

  std::vector<der::Input> ekus;
  EXPECT_FALSE(ParseEKUExtension(der::Input(not_a_sequence), &ekus));
}

// A sequence passed into ParseEKUExtension must have at least one oid in it.
TEST(ExtendedKeyUsageTest, EmptySequence) {
  const uint8_t empty_sequence[] = {0x30, 0x00};  // SEQUENCE (0 bytes)

  std::vector<der::Input> ekus;
  EXPECT_FALSE(ParseEKUExtension(der::Input(empty_sequence), &ekus));
}

// The extension value must not be empty.
TEST(ExtendedKeyUsageTest, EmptyExtension) {
  std::vector<der::Input> ekus;
  EXPECT_FALSE(ParseEKUExtension(der::Input(), &ekus));
}

}  // namespace

}  // namespace net
