| OLD | NEW |
| 1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include <string> | 5 #include <string> |
| 6 | 6 |
| 7 #include "base/basictypes.h" | 7 #include "base/basictypes.h" |
| 8 #include "base/logging.h" | 8 #include "base/logging.h" |
| 9 #include "base/memory/scoped_ptr.h" | 9 #include "base/memory/scoped_ptr.h" |
| 10 #include "base/strings/stringprintf.h" | 10 #include "base/strings/stringprintf.h" |
| (...skipping 29 matching lines...) Expand all Loading... |
| 40 | 40 |
| 41 // Mock of MediaPlayerManager for testing purpose. | 41 // Mock of MediaPlayerManager for testing purpose. |
| 42 class MockMediaPlayerManager : public MediaPlayerManager { | 42 class MockMediaPlayerManager : public MediaPlayerManager { |
| 43 public: | 43 public: |
| 44 explicit MockMediaPlayerManager(base::MessageLoop* message_loop) | 44 explicit MockMediaPlayerManager(base::MessageLoop* message_loop) |
| 45 : message_loop_(message_loop), | 45 : message_loop_(message_loop), |
| 46 playback_completed_(false), | 46 playback_completed_(false), |
| 47 num_resources_requested_(0), | 47 num_resources_requested_(0), |
| 48 num_metadata_changes_(0), | 48 num_metadata_changes_(0), |
| 49 timestamp_updated_(false), | 49 timestamp_updated_(false), |
| 50 is_audible_(false), | |
| 51 is_delay_expired_(false), | |
| 52 allow_play_(true) {} | 50 allow_play_(true) {} |
| 53 ~MockMediaPlayerManager() override {} | 51 ~MockMediaPlayerManager() override {} |
| 54 | 52 |
| 55 // MediaPlayerManager implementation. | 53 // MediaPlayerManager implementation. |
| 56 MediaResourceGetter* GetMediaResourceGetter() override { return NULL; } | 54 MediaResourceGetter* GetMediaResourceGetter() override { return NULL; } |
| 57 MediaUrlInterceptor* GetMediaUrlInterceptor() override { return NULL; } | 55 MediaUrlInterceptor* GetMediaUrlInterceptor() override { return NULL; } |
| 58 void OnTimeUpdate(int player_id, | 56 void OnTimeUpdate(int player_id, |
| 59 base::TimeDelta current_time, | 57 base::TimeDelta current_time, |
| 60 base::TimeTicks current_time_ticks) override { | 58 base::TimeTicks current_time_ticks) override { |
| 61 timestamp_updated_ = true; | 59 timestamp_updated_ = true; |
| (...skipping 17 matching lines...) Expand all Loading... |
| 79 void OnError(int player_id, int error) override {} | 77 void OnError(int player_id, int error) override {} |
| 80 void OnVideoSizeChanged(int player_id, int width, int height) override {} | 78 void OnVideoSizeChanged(int player_id, int width, int height) override {} |
| 81 void OnWaitingForDecryptionKey(int player_id) override {} | 79 void OnWaitingForDecryptionKey(int player_id) override {} |
| 82 MediaPlayerAndroid* GetFullscreenPlayer() override { return NULL; } | 80 MediaPlayerAndroid* GetFullscreenPlayer() override { return NULL; } |
| 83 MediaPlayerAndroid* GetPlayer(int player_id) override { return NULL; } | 81 MediaPlayerAndroid* GetPlayer(int player_id) override { return NULL; } |
| 84 | 82 |
| 85 bool RequestPlay(int player_id) override { | 83 bool RequestPlay(int player_id) override { |
| 86 return allow_play_; | 84 return allow_play_; |
| 87 } | 85 } |
| 88 | 86 |
| 89 void OnAudibleStateChanged(int player_id, bool is_audible_now) override { | |
| 90 is_audible_ = is_audible_now; | |
| 91 } | |
| 92 | |
| 93 bool playback_completed() const { | 87 bool playback_completed() const { |
| 94 return playback_completed_; | 88 return playback_completed_; |
| 95 } | 89 } |
| 96 | 90 |
| 97 int num_resources_requested() const { | 91 int num_resources_requested() const { |
| 98 return num_resources_requested_; | 92 return num_resources_requested_; |
| 99 } | 93 } |
| 100 | 94 |
| 101 int num_metadata_changes() const { | 95 int num_metadata_changes() const { |
| 102 return num_metadata_changes_; | 96 return num_metadata_changes_; |
| 103 } | 97 } |
| 104 | 98 |
| 105 void OnMediaResourcesRequested(int player_id) { | 99 void OnMediaResourcesRequested(int player_id) { |
| 106 num_resources_requested_++; | 100 num_resources_requested_++; |
| 107 } | 101 } |
| 108 | 102 |
| 109 bool timestamp_updated() const { | 103 bool timestamp_updated() const { |
| 110 return timestamp_updated_; | 104 return timestamp_updated_; |
| 111 } | 105 } |
| 112 | 106 |
| 113 void ResetTimestampUpdated() { | 107 void ResetTimestampUpdated() { |
| 114 timestamp_updated_ = false; | 108 timestamp_updated_ = false; |
| 115 } | 109 } |
| 116 | 110 |
| 117 bool is_audible() const { | |
| 118 return is_audible_; | |
| 119 } | |
| 120 | |
| 121 bool is_delay_expired() const { | |
| 122 return is_delay_expired_; | |
| 123 } | |
| 124 | |
| 125 void SetDelayExpired(bool value) { | |
| 126 is_delay_expired_ = value; | |
| 127 } | |
| 128 | |
| 129 void set_allow_play(bool value) { | 111 void set_allow_play(bool value) { |
| 130 allow_play_ = value; | 112 allow_play_ = value; |
| 131 } | 113 } |
| 132 | 114 |
| 133 private: | 115 private: |
| 134 base::MessageLoop* message_loop_; | 116 base::MessageLoop* message_loop_; |
| 135 bool playback_completed_; | 117 bool playback_completed_; |
| 136 // The number of resource requests this object has seen. | 118 // The number of resource requests this object has seen. |
| 137 int num_resources_requested_; | 119 int num_resources_requested_; |
| 138 // The number of metadata changes reported by the player. | 120 // The number of metadata changes reported by the player. |
| 139 int num_metadata_changes_; | 121 int num_metadata_changes_; |
| 140 // Playback timestamp was updated. | 122 // Playback timestamp was updated. |
| 141 bool timestamp_updated_; | 123 bool timestamp_updated_; |
| 142 // Audible state of the pipeline | |
| 143 bool is_audible_; | |
| 144 // Helper flag to ensure delay for WaitForDelay(). | |
| 145 bool is_delay_expired_; | |
| 146 // Whether the manager will allow players that request playing. | 124 // Whether the manager will allow players that request playing. |
| 147 bool allow_play_; | 125 bool allow_play_; |
| 148 | 126 |
| 149 DISALLOW_COPY_AND_ASSIGN(MockMediaPlayerManager); | 127 DISALLOW_COPY_AND_ASSIGN(MockMediaPlayerManager); |
| 150 }; | 128 }; |
| 151 | 129 |
| 152 class MockDemuxerAndroid : public DemuxerAndroid { | 130 class MockDemuxerAndroid : public DemuxerAndroid { |
| 153 public: | 131 public: |
| 154 explicit MockDemuxerAndroid(base::MessageLoop* message_loop) | 132 explicit MockDemuxerAndroid(base::MessageLoop* message_loop) |
| 155 : message_loop_(message_loop), | 133 : message_loop_(message_loop), |
| (...skipping 403 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 559 EXPECT_TRUE(GetMediaDecoderJob(is_audio)->is_decoding()); | 537 EXPECT_TRUE(GetMediaDecoderJob(is_audio)->is_decoding()); |
| 560 EXPECT_TRUE(GetMediaCodecBridge(is_audio)); | 538 EXPECT_TRUE(GetMediaCodecBridge(is_audio)); |
| 561 EXPECT_TRUE(!is_clock_manager || | 539 EXPECT_TRUE(!is_clock_manager || |
| 562 target_timestamp == player_.GetCurrentTime()); | 540 target_timestamp == player_.GetCurrentTime()); |
| 563 current_timestamp += 30; | 541 current_timestamp += 30; |
| 564 WaitForDecodeDone(is_audio, !is_audio); | 542 WaitForDecodeDone(is_audio, !is_audio); |
| 565 } | 543 } |
| 566 EXPECT_LE(target_timestamp, player_.GetCurrentTime()); | 544 EXPECT_LE(target_timestamp, player_.GetCurrentTime()); |
| 567 } | 545 } |
| 568 | 546 |
| 569 void PlayAudioForTimeInterval(const base::TimeDelta& start_timestamp, | |
| 570 const base::TimeDelta& target_timestamp ) { | |
| 571 | |
| 572 DemuxerData data = CreateReadFromDemuxerAckForAudio(1); | |
| 573 int current_timestamp = start_timestamp.InMilliseconds(); | |
| 574 int stop_timestamp = target_timestamp.InMilliseconds(); | |
| 575 while (current_timestamp < stop_timestamp) { | |
| 576 data.access_units[0].timestamp = | |
| 577 base::TimeDelta::FromMilliseconds(current_timestamp); | |
| 578 player_.OnDemuxerDataAvailable(data); | |
| 579 current_timestamp += 30; | |
| 580 WaitForAudioDecodeDone(); | |
| 581 } | |
| 582 } | |
| 583 | |
| 584 void WaitForDelay(const base::TimeDelta& delay) { | |
| 585 // Let the message_loop_ process events. | |
| 586 // We post delayed task and RunUnitilIdle() until it signals. | |
| 587 | |
| 588 manager_.SetDelayExpired(false); | |
| 589 message_loop_.PostDelayedTask( | |
| 590 FROM_HERE, | |
| 591 base::Bind(&MockMediaPlayerManager::SetDelayExpired, | |
| 592 base::Unretained(&manager_), | |
| 593 true), | |
| 594 delay); | |
| 595 | |
| 596 while (!manager_.is_delay_expired()) | |
| 597 message_loop_.RunUntilIdle(); | |
| 598 } | |
| 599 | |
| 600 DemuxerData CreateReadFromDemuxerAckWithConfigChanged( | 547 DemuxerData CreateReadFromDemuxerAckWithConfigChanged( |
| 601 bool is_audio, | 548 bool is_audio, |
| 602 int config_unit_index, | 549 int config_unit_index, |
| 603 const DemuxerConfigs& configs) { | 550 const DemuxerConfigs& configs) { |
| 604 DemuxerData data; | 551 DemuxerData data; |
| 605 data.type = is_audio ? DemuxerStream::AUDIO : DemuxerStream::VIDEO; | 552 data.type = is_audio ? DemuxerStream::AUDIO : DemuxerStream::VIDEO; |
| 606 data.access_units.resize(config_unit_index + 1); | 553 data.access_units.resize(config_unit_index + 1); |
| 607 | 554 |
| 608 for (int i = 0; i < config_unit_index; ++i) | 555 for (int i = 0; i < config_unit_index; ++i) |
| 609 data.access_units[i] = CreateAccessUnitWithData(is_audio, i, false); | 556 data.access_units[i] = CreateAccessUnitWithData(is_audio, i, false); |
| (...skipping 304 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 914 // surfaces, tests need to create a new surface texture without releasing | 861 // surfaces, tests need to create a new surface texture without releasing |
| 915 // their previous one. In CreateNextTextureAndSetVideoSurface(), we toggle | 862 // their previous one. In CreateNextTextureAndSetVideoSurface(), we toggle |
| 916 // between two surface textures, only replacing the N-2 texture. Assumption is | 863 // between two surface textures, only replacing the N-2 texture. Assumption is |
| 917 // that no more than N-1 texture is in use by decoder when | 864 // that no more than N-1 texture is in use by decoder when |
| 918 // CreateNextTextureAndSetVideoSurface() is called. | 865 // CreateNextTextureAndSetVideoSurface() is called. |
| 919 scoped_refptr<gfx::SurfaceTexture> surface_texture_a_; | 866 scoped_refptr<gfx::SurfaceTexture> surface_texture_a_; |
| 920 scoped_refptr<gfx::SurfaceTexture> surface_texture_b_; | 867 scoped_refptr<gfx::SurfaceTexture> surface_texture_b_; |
| 921 bool surface_texture_a_is_next_; | 868 bool surface_texture_a_is_next_; |
| 922 int next_texture_id_; | 869 int next_texture_id_; |
| 923 | 870 |
| 924 bool verify_not_audible_is_called_; | |
| 925 | |
| 926 DISALLOW_COPY_AND_ASSIGN(MediaSourcePlayerTest); | 871 DISALLOW_COPY_AND_ASSIGN(MediaSourcePlayerTest); |
| 927 }; | 872 }; |
| 928 | 873 |
| 929 TEST_F(MediaSourcePlayerTest, StartAudioDecoderWithValidConfig) { | 874 TEST_F(MediaSourcePlayerTest, StartAudioDecoderWithValidConfig) { |
| 930 SKIP_TEST_IF_MEDIA_CODEC_BRIDGE_IS_NOT_AVAILABLE(); | 875 SKIP_TEST_IF_MEDIA_CODEC_BRIDGE_IS_NOT_AVAILABLE(); |
| 931 | 876 |
| 932 // Test audio codec will be created when valid configs and data are passed to | 877 // Test audio codec will be created when valid configs and data are passed to |
| 933 // the audio decoder job. | 878 // the audio decoder job. |
| 934 StartAudioDecoderJob(); | 879 StartAudioDecoderJob(); |
| 935 EXPECT_EQ(0, demuxer_->num_seek_requests()); | 880 EXPECT_EQ(0, demuxer_->num_seek_requests()); |
| (...skipping 11 matching lines...) Expand all Loading... |
| 947 uint8 invalid_codec_data[] = { 0x00, 0xff, 0xff, 0xff, 0xff }; | 892 uint8 invalid_codec_data[] = { 0x00, 0xff, 0xff, 0xff, 0xff }; |
| 948 configs.audio_extra_data.insert(configs.audio_extra_data.begin(), | 893 configs.audio_extra_data.insert(configs.audio_extra_data.begin(), |
| 949 invalid_codec_data, invalid_codec_data + 4); | 894 invalid_codec_data, invalid_codec_data + 4); |
| 950 Start(configs); | 895 Start(configs); |
| 951 | 896 |
| 952 // Decoder is not created after data is received. | 897 // Decoder is not created after data is received. |
| 953 player_.OnDemuxerDataAvailable(CreateReadFromDemuxerAckForAudio(0)); | 898 player_.OnDemuxerDataAvailable(CreateReadFromDemuxerAckForAudio(0)); |
| 954 EXPECT_FALSE(GetMediaCodecBridge(true)); | 899 EXPECT_FALSE(GetMediaCodecBridge(true)); |
| 955 } | 900 } |
| 956 | 901 |
| 957 // timav | |
| 958 TEST_F(MediaSourcePlayerTest, AudioDecoderSetsAudibleState) { | |
| 959 SKIP_TEST_IF_MEDIA_CODEC_BRIDGE_IS_NOT_AVAILABLE(); | |
| 960 | |
| 961 // No data arrived yet | |
| 962 EXPECT_FALSE(manager_.is_audible()); | |
| 963 | |
| 964 // Initialize decoder | |
| 965 StartAudioDecoderJob(); | |
| 966 player_.SetVolume(1.0); | |
| 967 | |
| 968 // Process frames until prerolling is done. | |
| 969 SeekPlayerWithAbort(true, base::TimeDelta::FromMilliseconds(100)); | |
| 970 EXPECT_TRUE(IsPrerolling(true)); | |
| 971 PrerollDecoderToTime( | |
| 972 true, base::TimeDelta(), base::TimeDelta::FromMilliseconds(100), false); | |
| 973 EXPECT_TRUE(IsPrerolling(false)); | |
| 974 | |
| 975 // Send more packets | |
| 976 PlayAudioForTimeInterval(base::TimeDelta::FromMilliseconds(150), | |
| 977 base::TimeDelta::FromMilliseconds(220)); | |
| 978 | |
| 979 // The player should trigger audible status | |
| 980 EXPECT_TRUE(manager_.is_audible()); | |
| 981 | |
| 982 // The player release should report a non-audible state. | |
| 983 ReleasePlayer(); | |
| 984 EXPECT_FALSE(manager_.is_audible()); | |
| 985 } | |
| 986 | |
| 987 TEST_F(MediaSourcePlayerTest, AudioDecoderRemovesAudibleStateWhenPaused) { | |
| 988 SKIP_TEST_IF_MEDIA_CODEC_BRIDGE_IS_NOT_AVAILABLE(); | |
| 989 | |
| 990 // No data arrived yet | |
| 991 EXPECT_FALSE(manager_.is_audible()); | |
| 992 | |
| 993 // Initialize decoder | |
| 994 StartAudioDecoderJob(); | |
| 995 player_.SetVolume(1.0); | |
| 996 | |
| 997 // Process frames until prerolling is done. | |
| 998 SeekPlayerWithAbort(true, base::TimeDelta::FromMilliseconds(100)); | |
| 999 EXPECT_TRUE(IsPrerolling(true)); | |
| 1000 PrerollDecoderToTime( | |
| 1001 true, base::TimeDelta(), base::TimeDelta::FromMilliseconds(100), false); | |
| 1002 EXPECT_TRUE(IsPrerolling(false)); | |
| 1003 | |
| 1004 // Send more packets | |
| 1005 PlayAudioForTimeInterval(base::TimeDelta::FromMilliseconds(150), | |
| 1006 base::TimeDelta::FromMilliseconds(220)); | |
| 1007 | |
| 1008 // The player should trigger audible status | |
| 1009 EXPECT_TRUE(manager_.is_audible()); | |
| 1010 | |
| 1011 // Pause the player | |
| 1012 player_.Pause(true); | |
| 1013 | |
| 1014 // Send more packets | |
| 1015 PlayAudioForTimeInterval(base::TimeDelta::FromMilliseconds(240), | |
| 1016 base::TimeDelta::FromMilliseconds(280)); | |
| 1017 | |
| 1018 // The player should trigger audible status again | |
| 1019 EXPECT_FALSE(manager_.is_audible()); | |
| 1020 | |
| 1021 player_.Release(); | |
| 1022 } | |
| 1023 | |
| 1024 TEST_F(MediaSourcePlayerTest, AudioDecoderRemovesAudibleStateWhenIdle) { | |
| 1025 SKIP_TEST_IF_MEDIA_CODEC_BRIDGE_IS_NOT_AVAILABLE(); | |
| 1026 | |
| 1027 // No data arrived yet | |
| 1028 EXPECT_FALSE(manager_.is_audible()); | |
| 1029 | |
| 1030 // Initialize decoder | |
| 1031 StartAudioDecoderJob(); | |
| 1032 player_.SetVolume(1.0); | |
| 1033 | |
| 1034 // Process frames until prerolling is done. | |
| 1035 SeekPlayerWithAbort(true, base::TimeDelta::FromMilliseconds(100)); | |
| 1036 EXPECT_TRUE(IsPrerolling(true)); | |
| 1037 PrerollDecoderToTime( | |
| 1038 true, base::TimeDelta(), base::TimeDelta::FromMilliseconds(100), false); | |
| 1039 EXPECT_TRUE(IsPrerolling(false)); | |
| 1040 | |
| 1041 // Send more packets | |
| 1042 PlayAudioForTimeInterval(base::TimeDelta::FromMilliseconds(150), | |
| 1043 base::TimeDelta::FromMilliseconds(220)); | |
| 1044 | |
| 1045 // The player should trigger audible status | |
| 1046 EXPECT_TRUE(manager_.is_audible()); | |
| 1047 | |
| 1048 // Simulate the freeze on demuxer: wait for 300 ms | |
| 1049 WaitForDelay(base::TimeDelta::FromMilliseconds(300)); | |
| 1050 | |
| 1051 // By this time the player should have reported | |
| 1052 // that there is no audio. | |
| 1053 EXPECT_FALSE(manager_.is_audible()); | |
| 1054 | |
| 1055 ReleasePlayer(); | |
| 1056 } | |
| 1057 | |
| 1058 TEST_F(MediaSourcePlayerTest, StartVideoCodecWithValidSurface) { | 902 TEST_F(MediaSourcePlayerTest, StartVideoCodecWithValidSurface) { |
| 1059 SKIP_TEST_IF_MEDIA_CODEC_BRIDGE_IS_NOT_AVAILABLE(); | 903 SKIP_TEST_IF_MEDIA_CODEC_BRIDGE_IS_NOT_AVAILABLE(); |
| 1060 | 904 |
| 1061 // Test video codec will not be created until data is received. | 905 // Test video codec will not be created until data is received. |
| 1062 StartVideoDecoderJob(); | 906 StartVideoDecoderJob(); |
| 1063 | 907 |
| 1064 // Set both an initial and a later video surface without receiving any | 908 // Set both an initial and a later video surface without receiving any |
| 1065 // demuxed data yet. | 909 // demuxed data yet. |
| 1066 CreateNextTextureAndSetVideoSurface(); | 910 CreateNextTextureAndSetVideoSurface(); |
| 1067 EXPECT_FALSE(GetMediaCodecBridge(false)); | 911 EXPECT_FALSE(GetMediaCodecBridge(false)); |
| (...skipping 1493 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2561 | 2405 |
| 2562 EXPECT_EQ(demuxer_->num_data_requests(), 0); | 2406 EXPECT_EQ(demuxer_->num_data_requests(), 0); |
| 2563 player_.OnDemuxerConfigsAvailable(CreateDemuxerConfigs(true, true)); | 2407 player_.OnDemuxerConfigsAvailable(CreateDemuxerConfigs(true, true)); |
| 2564 | 2408 |
| 2565 manager_.set_allow_play(true); | 2409 manager_.set_allow_play(true); |
| 2566 player_.Start(); | 2410 player_.Start(); |
| 2567 EXPECT_TRUE(player_.IsPlaying()); | 2411 EXPECT_TRUE(player_.IsPlaying()); |
| 2568 } | 2412 } |
| 2569 | 2413 |
| 2570 } // namespace media | 2414 } // namespace media |
| OLD | NEW |