// Copyright 2014 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 "media/formats/webm/cluster_builder.h"
#include "media/formats/webm/webm_constants.h"
#include "media/formats/webm/webm_parser.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"

using ::testing::InSequence;
using ::testing::Return;
using ::testing::ReturnNull;
using ::testing::StrictMock;
using ::testing::_;

namespace media {

enum { kBlockCount = 5 };

class MockWebMParserClient : public WebMParserClient {
 public:
  virtual ~MockWebMParserClient() {}

  // WebMParserClient methods.
  MOCK_METHOD1(OnListStart, WebMParserClient*(int));
  MOCK_METHOD1(OnListEnd, bool(int));
  MOCK_METHOD2(OnUInt, bool(int, int64));
  MOCK_METHOD2(OnFloat, bool(int, double));
  MOCK_METHOD3(OnBinary, bool(int, const uint8*, int));
  MOCK_METHOD2(OnString, bool(int, const std::string&));
};

class WebMParserTest : public testing::Test {
 protected:
  StrictMock<MockWebMParserClient> client_;
};

static scoped_ptr<Cluster> CreateCluster(int block_count) {
  ClusterBuilder cb;
  cb.SetClusterTimecode(0);

  for (int i = 0; i < block_count; i++) {
    uint8 data[] = { 0x00 };
    cb.AddSimpleBlock(0, i, 0, data, sizeof(data));
  }

  return cb.Finish();
}

static void CreateClusterExpectations(int block_count,
                                      bool is_complete_cluster,
                                      MockWebMParserClient* client) {

  InSequence s;
  EXPECT_CALL(*client, OnListStart(kWebMIdCluster)).WillOnce(Return(client));
  EXPECT_CALL(*client, OnUInt(kWebMIdTimecode, 0))
      .WillOnce(Return(true));

  for (int i = 0; i < block_count; i++) {
    EXPECT_CALL(*client, OnBinary(kWebMIdSimpleBlock, _, _))
        .WillOnce(Return(true));
  }

  if (is_complete_cluster)
    EXPECT_CALL(*client, OnListEnd(kWebMIdCluster)).WillOnce(Return(true));
}

TEST_F(WebMParserTest, EmptyCluster) {
  const uint8 kEmptyCluster[] = {
    0x1F, 0x43, 0xB6, 0x75, 0x80  // CLUSTER (size = 0)
  };
  int size = sizeof(kEmptyCluster);

  InSequence s;
  EXPECT_CALL(client_, OnListStart(kWebMIdCluster)).WillOnce(Return(&client_));
  EXPECT_CALL(client_, OnListEnd(kWebMIdCluster)).WillOnce(Return(true));

  WebMListParser parser(kWebMIdCluster, &client_);
  EXPECT_EQ(size, parser.Parse(kEmptyCluster, size));
  EXPECT_TRUE(parser.IsParsingComplete());
}

TEST_F(WebMParserTest, EmptyClusterInSegment) {
  const uint8 kBuffer[] = {
    0x18, 0x53, 0x80, 0x67, 0x85,  // SEGMENT (size = 5)
    0x1F, 0x43, 0xB6, 0x75, 0x80,  // CLUSTER (size = 0)
  };
  int size = sizeof(kBuffer);

  InSequence s;
  EXPECT_CALL(client_, OnListStart(kWebMIdSegment)).WillOnce(Return(&client_));
  EXPECT_CALL(client_, OnListStart(kWebMIdCluster)).WillOnce(Return(&client_));
  EXPECT_CALL(client_, OnListEnd(kWebMIdCluster)).WillOnce(Return(true));
  EXPECT_CALL(client_, OnListEnd(kWebMIdSegment)).WillOnce(Return(true));

  WebMListParser parser(kWebMIdSegment, &client_);
  EXPECT_EQ(size, parser.Parse(kBuffer, size));
  EXPECT_TRUE(parser.IsParsingComplete());
}

// Test the case where a non-list child element has a size
// that is beyond the end of the parent.
TEST_F(WebMParserTest, ChildNonListLargerThanParent) {
  const uint8 kBuffer[] = {
    0x1F, 0x43, 0xB6, 0x75, 0x81,  // CLUSTER (size = 1)
    0xE7, 0x81, 0x01,  // Timecode (size=1, value=1)
  };

  InSequence s;
  EXPECT_CALL(client_, OnListStart(kWebMIdCluster)).WillOnce(Return(&client_));

  WebMListParser parser(kWebMIdCluster, &client_);
  EXPECT_EQ(-1, parser.Parse(kBuffer, sizeof(kBuffer)));
  EXPECT_FALSE(parser.IsParsingComplete());
}

// Test the case where a list child element has a size
// that is beyond the end of the parent.
TEST_F(WebMParserTest, ChildListLargerThanParent) {
  const uint8 kBuffer[] = {
    0x18, 0x53, 0x80, 0x67, 0x85,  // SEGMENT (size = 5)
    0x1F, 0x43, 0xB6, 0x75, 0x81, 0x11  // CLUSTER (size = 1)
  };

  InSequence s;
  EXPECT_CALL(client_, OnListStart(kWebMIdSegment)).WillOnce(Return(&client_));

  WebMListParser parser(kWebMIdSegment, &client_);
  EXPECT_EQ(-1, parser.Parse(kBuffer, sizeof(kBuffer)));
  EXPECT_FALSE(parser.IsParsingComplete());
}

// Expecting to parse a Cluster, but get a Segment.
TEST_F(WebMParserTest, ListIdDoesNotMatch) {
  const uint8 kBuffer[] = {
    0x18, 0x53, 0x80, 0x67, 0x80,  // SEGMENT (size = 0)
  };

  WebMListParser parser(kWebMIdCluster, &client_);
  EXPECT_EQ(-1, parser.Parse(kBuffer, sizeof(kBuffer)));
  EXPECT_FALSE(parser.IsParsingComplete());
}

TEST_F(WebMParserTest, InvalidElementInList) {
  const uint8 kBuffer[] = {
    0x18, 0x53, 0x80, 0x67, 0x82,  // SEGMENT (size = 2)
    0xAE, 0x80,  // TrackEntry (size = 0)
  };

  InSequence s;
  EXPECT_CALL(client_, OnListStart(kWebMIdSegment)).WillOnce(Return(&client_));

  WebMListParser parser(kWebMIdSegment, &client_);
  EXPECT_EQ(-1, parser.Parse(kBuffer, sizeof(kBuffer)));
  EXPECT_FALSE(parser.IsParsingComplete());
}

// Test specific case of InvalidElementInList to verify EBMLHEADER within
// known-sized cluster causes parse error.
TEST_F(WebMParserTest, InvalidEBMLHeaderInCluster) {
  const uint8 kBuffer[] = {
    0x1F, 0x43, 0xB6, 0x75, 0x85,  // CLUSTER (size = 5)
    0x1A, 0x45, 0xDF, 0xA3, 0x80,    // EBMLHEADER (size = 0)
  };

  InSequence s;
  EXPECT_CALL(client_, OnListStart(kWebMIdCluster)).WillOnce(Return(&client_));

  WebMListParser parser(kWebMIdCluster, &client_);
  EXPECT_EQ(-1, parser.Parse(kBuffer, sizeof(kBuffer)));
  EXPECT_FALSE(parser.IsParsingComplete());
}

// Verify that EBMLHEADER ends a preceding "unknown"-sized CLUSTER.
TEST_F(WebMParserTest, UnknownSizeClusterFollowedByEBMLHeader) {
  const uint8 kBuffer[] = {
    0x1F, 0x43, 0xB6, 0x75, 0xFF,  // CLUSTER (size = unknown; really 0 due to:)
    0x1A, 0x45, 0xDF, 0xA3, 0x80,  // EBMLHEADER (size = 0)
  };

  InSequence s;
  EXPECT_CALL(client_, OnListStart(kWebMIdCluster)).WillOnce(Return(&client_));
  EXPECT_CALL(client_, OnListEnd(kWebMIdCluster)).WillOnce(Return(true));

  WebMListParser parser(kWebMIdCluster, &client_);

  // List parse should consume the CLUSTER but not the EBMLHEADER.
  EXPECT_EQ(5, parser.Parse(kBuffer, sizeof(kBuffer)));
  EXPECT_TRUE(parser.IsParsingComplete());
}

TEST_F(WebMParserTest, VoidAndCRC32InList) {
  const uint8 kBuffer[] = {
    0x18, 0x53, 0x80, 0x67, 0x99,  // SEGMENT (size = 25)
    0xEC, 0x83, 0x00, 0x00, 0x00,  // Void (size = 3)
    0xBF, 0x83, 0x00, 0x00, 0x00,  // CRC32 (size = 3)
    0x1F, 0x43, 0xB6, 0x75, 0x8A,  // CLUSTER (size = 10)
    0xEC, 0x83, 0x00, 0x00, 0x00,  // Void (size = 3)
    0xBF, 0x83, 0x00, 0x00, 0x00,  // CRC32 (size = 3)
  };
  int size = sizeof(kBuffer);

  InSequence s;
  EXPECT_CALL(client_, OnListStart(kWebMIdSegment)).WillOnce(Return(&client_));
  EXPECT_CALL(client_, OnListStart(kWebMIdCluster)).WillOnce(Return(&client_));
  EXPECT_CALL(client_, OnListEnd(kWebMIdCluster)).WillOnce(Return(true));
  EXPECT_CALL(client_, OnListEnd(kWebMIdSegment)).WillOnce(Return(true));

  WebMListParser parser(kWebMIdSegment, &client_);
  EXPECT_EQ(size, parser.Parse(kBuffer, size));
  EXPECT_TRUE(parser.IsParsingComplete());
}


TEST_F(WebMParserTest, ParseListElementWithSingleCall) {
  scoped_ptr<Cluster> cluster(CreateCluster(kBlockCount));
  CreateClusterExpectations(kBlockCount, true, &client_);

  WebMListParser parser(kWebMIdCluster, &client_);
  EXPECT_EQ(cluster->size(), parser.Parse(cluster->data(), cluster->size()));
  EXPECT_TRUE(parser.IsParsingComplete());
}

TEST_F(WebMParserTest, ParseListElementWithMultipleCalls) {
  scoped_ptr<Cluster> cluster(CreateCluster(kBlockCount));
  CreateClusterExpectations(kBlockCount, true, &client_);

  const uint8* data = cluster->data();
  int size = cluster->size();
  int default_parse_size = 3;
  WebMListParser parser(kWebMIdCluster, &client_);
  int parse_size = std::min(default_parse_size, size);

  while (size > 0) {
    int result = parser.Parse(data, parse_size);
    ASSERT_GE(result, 0);
    ASSERT_LE(result, parse_size);

    if (result == 0) {
      // The parser needs more data so increase the parse_size a little.
      EXPECT_FALSE(parser.IsParsingComplete());
      parse_size += default_parse_size;
      parse_size = std::min(parse_size, size);
      continue;
    }

    parse_size = default_parse_size;

    data += result;
    size -= result;

    EXPECT_EQ((size == 0), parser.IsParsingComplete());
  }
  EXPECT_TRUE(parser.IsParsingComplete());
}

TEST_F(WebMParserTest, Reset) {
  InSequence s;
  scoped_ptr<Cluster> cluster(CreateCluster(kBlockCount));

  // First expect all but the last block.
  CreateClusterExpectations(kBlockCount - 1, false, &client_);

  // Now expect all blocks.
  CreateClusterExpectations(kBlockCount, true, &client_);

  WebMListParser parser(kWebMIdCluster, &client_);

  // Send slightly less than the full cluster so all but the last block is
  // parsed.
  int result = parser.Parse(cluster->data(), cluster->size() - 1);
  EXPECT_GT(result, 0);
  EXPECT_LT(result, cluster->size());
  EXPECT_FALSE(parser.IsParsingComplete());

  parser.Reset();

  // Now parse a whole cluster to verify that all the blocks will get parsed.
  EXPECT_EQ(cluster->size(), parser.Parse(cluster->data(), cluster->size()));
  EXPECT_TRUE(parser.IsParsingComplete());
}

// Test the case where multiple clients are used for different lists.
TEST_F(WebMParserTest, MultipleClients) {
  const uint8 kBuffer[] = {
    0x18, 0x53, 0x80, 0x67, 0x94,  // SEGMENT (size = 20)
    0x16, 0x54, 0xAE, 0x6B, 0x85,  //   TRACKS (size = 5)
    0xAE, 0x83,                    //     TRACKENTRY (size = 3)
    0xD7, 0x81, 0x01,              //       TRACKNUMBER (size = 1)
    0x1F, 0x43, 0xB6, 0x75, 0x85,  //   CLUSTER (size = 5)
    0xEC, 0x83, 0x00, 0x00, 0x00,  //     Void (size = 3)
  };
  int size = sizeof(kBuffer);

  StrictMock<MockWebMParserClient> c1_;
  StrictMock<MockWebMParserClient> c2_;
  StrictMock<MockWebMParserClient> c3_;

  InSequence s;
  EXPECT_CALL(client_, OnListStart(kWebMIdSegment)).WillOnce(Return(&c1_));
  EXPECT_CALL(c1_, OnListStart(kWebMIdTracks)).WillOnce(Return(&c2_));
  EXPECT_CALL(c2_, OnListStart(kWebMIdTrackEntry)).WillOnce(Return(&c3_));
  EXPECT_CALL(c3_, OnUInt(kWebMIdTrackNumber, 1)).WillOnce(Return(true));
  EXPECT_CALL(c2_, OnListEnd(kWebMIdTrackEntry)).WillOnce(Return(true));
  EXPECT_CALL(c1_, OnListEnd(kWebMIdTracks)).WillOnce(Return(true));
  EXPECT_CALL(c1_, OnListStart(kWebMIdCluster)).WillOnce(Return(&c2_));
  EXPECT_CALL(c1_, OnListEnd(kWebMIdCluster)).WillOnce(Return(true));
  EXPECT_CALL(client_, OnListEnd(kWebMIdSegment)).WillOnce(Return(true));

  WebMListParser parser(kWebMIdSegment, &client_);
  EXPECT_EQ(size, parser.Parse(kBuffer, size));
  EXPECT_TRUE(parser.IsParsingComplete());
}

// Test the case where multiple clients are used for different lists.
TEST_F(WebMParserTest, InvalidClient) {
  const uint8 kBuffer[] = {
    0x18, 0x53, 0x80, 0x67, 0x85,  // SEGMENT (size = 20)
    0x16, 0x54, 0xAE, 0x6B, 0x80,  //   TRACKS (size = 5)
  };

  InSequence s;
  EXPECT_CALL(client_, OnListStart(kWebMIdSegment)).WillOnce(ReturnNull());

  WebMListParser parser(kWebMIdSegment, &client_);
  EXPECT_EQ(-1, parser.Parse(kBuffer, sizeof(kBuffer)));
  EXPECT_FALSE(parser.IsParsingComplete());
}

TEST_F(WebMParserTest, ReservedIds) {
  const uint8 k1ByteReservedId[] = { 0xFF, 0x81 };
  const uint8 k2ByteReservedId[] = { 0x7F, 0xFF, 0x81 };
  const uint8 k3ByteReservedId[] = { 0x3F, 0xFF, 0xFF, 0x81 };
  const uint8 k4ByteReservedId[] = { 0x1F, 0xFF, 0xFF, 0xFF, 0x81 };
  const uint8* kBuffers[] = {
    k1ByteReservedId,
    k2ByteReservedId,
    k3ByteReservedId,
    k4ByteReservedId
  };

  for (size_t i = 0; i < arraysize(kBuffers); i++) {
    int id;
    int64 element_size;
    int buffer_size = 2 + i;
    EXPECT_EQ(buffer_size, WebMParseElementHeader(kBuffers[i], buffer_size,
                                                  &id, &element_size));
    EXPECT_EQ(id, kWebMReservedId);
    EXPECT_EQ(element_size, 1);
  }
}

TEST_F(WebMParserTest, ReservedSizes) {
  const uint8 k1ByteReservedSize[] = { 0xA3, 0xFF };
  const uint8 k2ByteReservedSize[] = { 0xA3, 0x7F, 0xFF };
  const uint8 k3ByteReservedSize[] = { 0xA3, 0x3F, 0xFF, 0xFF };
  const uint8 k4ByteReservedSize[] = { 0xA3, 0x1F, 0xFF, 0xFF, 0xFF };
  const uint8 k5ByteReservedSize[] = { 0xA3, 0x0F, 0xFF, 0xFF, 0xFF, 0xFF };
  const uint8 k6ByteReservedSize[] = { 0xA3, 0x07, 0xFF, 0xFF, 0xFF, 0xFF,
                                       0xFF };
  const uint8 k7ByteReservedSize[] = { 0xA3, 0x03, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
                                       0xFF };
  const uint8 k8ByteReservedSize[] = { 0xA3, 0x01, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
                                       0xFF, 0xFF };
  const uint8* kBuffers[] = {
    k1ByteReservedSize,
    k2ByteReservedSize,
    k3ByteReservedSize,
    k4ByteReservedSize,
    k5ByteReservedSize,
    k6ByteReservedSize,
    k7ByteReservedSize,
    k8ByteReservedSize
  };

  for (size_t i = 0; i < arraysize(kBuffers); i++) {
    int id;
    int64 element_size;
    int buffer_size = 2 + i;
    EXPECT_EQ(buffer_size, WebMParseElementHeader(kBuffers[i], buffer_size,
                                                  &id, &element_size));
    EXPECT_EQ(id, 0xA3);
    EXPECT_EQ(element_size, kWebMUnknownSize);
  }
}

TEST_F(WebMParserTest, ZeroPaddedStrings) {
  const uint8 kBuffer[] = {
    0x1A, 0x45, 0xDF, 0xA3, 0x91,  // EBMLHEADER (size = 17)
    0x42, 0x82, 0x80,  // DocType (size = 0)
    0x42, 0x82, 0x81, 0x00,  // DocType (size = 1) ""
    0x42, 0x82, 0x81, 'a',  // DocType (size = 1) "a"
    0x42, 0x82, 0x83, 'a', 0x00, 0x00  // DocType (size = 3) "a"
  };
  int size = sizeof(kBuffer);

  InSequence s;
  EXPECT_CALL(client_, OnListStart(kWebMIdEBMLHeader))
      .WillOnce(Return(&client_));
  EXPECT_CALL(client_, OnString(kWebMIdDocType, "")).WillOnce(Return(true));
  EXPECT_CALL(client_, OnString(kWebMIdDocType, "")).WillOnce(Return(true));
  EXPECT_CALL(client_, OnString(kWebMIdDocType, "a")).WillOnce(Return(true));
  EXPECT_CALL(client_, OnString(kWebMIdDocType, "a")).WillOnce(Return(true));
  EXPECT_CALL(client_, OnListEnd(kWebMIdEBMLHeader)).WillOnce(Return(true));

  WebMListParser parser(kWebMIdEBMLHeader, &client_);
  EXPECT_EQ(size, parser.Parse(kBuffer, size));
  EXPECT_TRUE(parser.IsParsingComplete());
}

}  // namespace media
