dawn::wire::client: Remove linked list mechanism from ObjectBase Instead, iterate over the lists of all objects in the ObjectStore Bug: 344963953 Change-Id: I32bab41068a9c3daadad747c6ff8cce1156bee60 Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/197457 Reviewed-by: Loko Kung <lokokung@google.com> Commit-Queue: Corentin Wallez <cwallez@chromium.org> Reviewed-by: Austin Eng <enga@chromium.org>
diff --git a/src/dawn/wire/client/Client.cpp b/src/dawn/wire/client/Client.cpp index ae371ae..0f50540 100644 --- a/src/dawn/wire/client/Client.cpp +++ b/src/dawn/wire/client/Client.cpp
@@ -70,9 +70,10 @@ void Client::UnregisterAllObjects() { for (auto& objectList : mObjects) { - while (!objectList.empty()) { - ObjectBase* object = objectList.head()->value(); - object->Unregister(); + for (auto object : objectList.GetAllObjects()) { + if (object != nullptr) { + object->Unregister(); + } } } } @@ -160,18 +161,20 @@ eventManager->TransitionTo(EventManager::State::ClientDropped); } - auto& deviceList = mObjects[ObjectType::Device]; { - for (LinkNode<ObjectBase>* device = deviceList.head(); device != deviceList.end(); - device = device->next()) { - static_cast<Device*>(device->value()) - ->HandleDeviceLost(WGPUDeviceLostReason_Unknown, "GPU connection lost"); + auto& deviceList = mObjects[ObjectType::Device]; + for (auto object : deviceList.GetAllObjects()) { + if (object != nullptr) { + static_cast<Device*>(object)->HandleDeviceLost(WGPUDeviceLostReason_Unknown, + "GPU connection lost"); + } } } for (auto& objectList : mObjects) { - for (LinkNode<ObjectBase>* object = objectList.head(); object != objectList.end(); - object = object->next()) { - object->value()->CancelCallbacksForDisconnect(); + for (auto object : objectList.GetAllObjects()) { + if (object != nullptr) { + object->CancelCallbacksForDisconnect(); + } } } } @@ -190,8 +193,7 @@ } void Client::ReclaimReservation(ObjectBase* obj, ObjectType type) { - mObjectStores[type].Remove(obj); - obj->RemoveFromList(); + mObjects[type].Remove(obj); } } // namespace dawn::wire::client
diff --git a/src/dawn/wire/client/Client.h b/src/dawn/wire/client/Client.h index e3c0bf5..08d4d11 100644 --- a/src/dawn/wire/client/Client.h +++ b/src/dawn/wire/client/Client.h
@@ -63,11 +63,10 @@ Ref<T> Make(Args&&... args) { constexpr ObjectType type = ObjectTypeToTypeEnum<T>; - ObjectBaseParams params = {this, mObjectStores[type].ReserveHandle()}; + ObjectBaseParams params = {this, mObjects[type].ReserveHandle()}; Ref<T> object = AcquireRef(new T(params, std::forward<Args>(args)...)); - mObjects[type].Append(object.Get()); - mObjectStores[type].Insert(object.Get()); + mObjects[type].Insert(object.Get()); return object; } @@ -76,7 +75,7 @@ template <typename T> T* Get(ObjectId id) { - return static_cast<T*>(mObjectStores[ObjectTypeToTypeEnum<T>].Get(id)); + return static_cast<T*>(mObjects[ObjectTypeToTypeEnum<T>].Get(id)); } // ChunkedCommandHandler implementation @@ -124,10 +123,9 @@ ChunkedCommandSerializer mSerializer; WireDeserializeAllocator mWireCommandAllocator; - PerObjectType<ObjectStore> mObjectStores; + PerObjectType<ObjectStore> mObjects; std::unique_ptr<MemoryTransferService> mOwnedMemoryTransferService = nullptr; raw_ptr<MemoryTransferService> mMemoryTransferService = nullptr; - PerObjectType<LinkedList<ObjectBase>> mObjects; // Map of instance object handles to a corresponding event manager. Note that for now because we // do not have an internal refcount on the instances, i.e. we don't know when the last object // associated with a particular instance is destroyed, this map is not cleaned up until the
diff --git a/src/dawn/wire/client/ObjectBase.h b/src/dawn/wire/client/ObjectBase.h index e1bf928..1a358b7 100644 --- a/src/dawn/wire/client/ObjectBase.h +++ b/src/dawn/wire/client/ObjectBase.h
@@ -31,7 +31,6 @@ #include "dawn/webgpu.h" #include "partition_alloc/pointers/raw_ptr.h" -#include "dawn/common/LinkedList.h" #include "dawn/common/Ref.h" #include "dawn/common/RefCounted.h" #include "dawn/wire/ObjectHandle.h" @@ -51,8 +50,7 @@ // - A pointer to the Client to get where to serialize commands // - The external reference count, starting at 1. // - An ID that is used to refer to this object when talking with the server side -// - A next/prev pointer. They are part of a linked list of objects of the same type. -class ObjectBase : public RefCounted, public LinkNode<ObjectBase> { +class ObjectBase : public RefCounted { public: explicit ObjectBase(const ObjectBaseParams& params);
diff --git a/src/dawn/wire/client/ObjectStore.cpp b/src/dawn/wire/client/ObjectStore.cpp index 08ba876..8333e0d 100644 --- a/src/dawn/wire/client/ObjectStore.cpp +++ b/src/dawn/wire/client/ObjectStore.cpp
@@ -63,7 +63,6 @@ } void ObjectStore::Remove(ObjectBase* obj) { - DAWN_ASSERT(obj->IsInList()); // The wire reuses ID for objects to keep them in a packed array starting from 0. // To avoid issues with asynchronous server->client communication referring to an ID that's // already reused, each handle also has a generation that's increment by one on each reuse. @@ -75,6 +74,10 @@ mObjects[currentHandle.id] = nullptr; } +const std::vector<raw_ptr<ObjectBase>>& ObjectStore::GetAllObjects() const { + return mObjects; +} + ObjectBase* ObjectStore::Get(ObjectId id) const { if (id >= mObjects.size()) { return nullptr;
diff --git a/src/dawn/wire/client/ObjectStore.h b/src/dawn/wire/client/ObjectStore.h index 9bf3bd2..6280236 100644 --- a/src/dawn/wire/client/ObjectStore.h +++ b/src/dawn/wire/client/ObjectStore.h
@@ -51,7 +51,9 @@ ObjectHandle ReserveHandle(); void Insert(ObjectBase* obj); void Remove(ObjectBase* obj); + ObjectBase* Get(ObjectId id) const; + const std::vector<raw_ptr<ObjectBase>>& GetAllObjects() const; private: uint32_t mCurrentId;