De-duplicate DRM acquire & release events by EventDispatcher
When we add DRM pre-acquire support to SampleQueue, we'll dispatch twice the number of acquire and release events. This is slightly confusing, since there's the same number of DrmSessionManager#acquireSession() calls. We can mitigate this by only dispatching each acquire and release event to at most one EventDispatcher. This also changes the events fired when playing a stream with both audio and video encrypted with the same keys (even without pre-acquisition). Before: The EventDispatcher would see 2 aquires, 1 key load and 2 release events. After: The EventDispatcher will see 1 acquire, 1 key load and 1 release. PiperOrigin-RevId: 358804502
This commit is contained in:
parent
0eed19d8a3
commit
623597addb
@ -32,6 +32,11 @@
|
||||
* Fix a bug with playback of ads in playlists, where the incorrect period
|
||||
index was used when deciding whether to trigger playback of an ad after
|
||||
a seek.
|
||||
* DRM:
|
||||
* Only dispatch DRM session acquire and release events once per period
|
||||
when playing content that uses the same encryption keys for both audio &
|
||||
video tracks (previously separate acquire and release events were
|
||||
dispatched for each track in each period).
|
||||
* VP9 extension: Update to use NDK r22
|
||||
([#8581](https://github.com/google/ExoPlayer/issues/8581)).
|
||||
* FLAC extension: Update to use NDK r22
|
||||
|
@ -138,4 +138,11 @@ public final class CopyOnWriteMultiset<E extends Object> implements Iterable<E>
|
||||
return elements.iterator();
|
||||
}
|
||||
}
|
||||
|
||||
/** Returns the number of occurrences of an element in this multiset. */
|
||||
public int count(E element) {
|
||||
synchronized (lock) {
|
||||
return elementCounts.containsKey(element) ? elementCounts.get(element) : 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -107,4 +107,14 @@ public final class CopyOnWriteMultisetTest {
|
||||
|
||||
assertThrows(UnsupportedOperationException.class, () -> elementSet.remove("a string"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void count() {
|
||||
CopyOnWriteMultiset<String> multiset = new CopyOnWriteMultiset<>();
|
||||
multiset.add("a string");
|
||||
multiset.add("a string");
|
||||
|
||||
assertThat(multiset.count("a string")).isEqualTo(2);
|
||||
assertThat(multiset.count("another string")).isEqualTo(0);
|
||||
}
|
||||
}
|
||||
|
@ -293,8 +293,11 @@ import org.checkerframework.checker.nullness.qual.RequiresNonNull;
|
||||
if (openInternal(true)) {
|
||||
doLicense(true);
|
||||
}
|
||||
} else if (eventDispatcher != null && isOpen()) {
|
||||
// If the session is already open then send the acquire event only to the provided dispatcher.
|
||||
} else if (eventDispatcher != null
|
||||
&& isOpen()
|
||||
&& eventDispatchers.count(eventDispatcher) == 1) {
|
||||
// If the session is already open and this is the first instance of eventDispatcher we've
|
||||
// seen, then send the acquire event only to the provided dispatcher.
|
||||
// TODO: Add a parameter to onDrmSessionAcquired to indicate whether the session is being
|
||||
// re-used or not.
|
||||
eventDispatcher.drmSessionAcquired();
|
||||
@ -323,9 +326,11 @@ import org.checkerframework.checker.nullness.qual.RequiresNonNull;
|
||||
}
|
||||
}
|
||||
if (eventDispatcher != null) {
|
||||
// Acquire and release events are only sent to the provided dispatcher.
|
||||
eventDispatcher.drmSessionReleased();
|
||||
eventDispatchers.remove(eventDispatcher);
|
||||
if (eventDispatchers.count(eventDispatcher) == 0) {
|
||||
// Release events are only sent to the last-attached instance of each EventDispatcher.
|
||||
eventDispatcher.drmSessionReleased();
|
||||
}
|
||||
}
|
||||
referenceCountListener.onReferenceCountDecremented(this, referenceCount);
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user