Skip to content

Commit 86c91dc

Browse files
chinmaygardednfield
authored andcommitted
Fix pipeline library issue related to not tracking pending futures.
1 parent 0b63e2c commit 86c91dc

File tree

7 files changed

+35
-28
lines changed

7 files changed

+35
-28
lines changed

impeller/display_list/display_list_dispatcher.cc

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -473,4 +473,8 @@ void DisplayListDispatcher::drawShadow(const SkPath& path,
473473
UNIMPLEMENTED;
474474
}
475475

476+
Picture DisplayListDispatcher::EndRecordingAsPicture() {
477+
return canvas_.EndRecordingAsPicture();
478+
}
479+
476480
} // namespace impeller

impeller/display_list/display_list_dispatcher.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,8 @@ class DisplayListDispatcher final : public flutter::Dispatcher {
1818

1919
~DisplayListDispatcher();
2020

21+
Picture EndRecordingAsPicture();
22+
2123
// |flutter::Dispatcher|
2224
void setAntiAlias(bool aa) override;
2325

impeller/entity/content_context.cc

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@
44

55
#include "impeller/entity/content_context.h"
66

7+
#include <sstream>
8+
79
namespace impeller {
810

911
ContentContext::ContentContext(std::shared_ptr<Context> context)
@@ -23,6 +25,7 @@ ContentContext::ContentContext(std::shared_ptr<Context> context)
2325
// Pipelines that are variants of the base pipelines with custom descriptors.
2426
if (auto solid_fill_pipeline = solid_fill_pipelines_[{}]->WaitAndGet()) {
2527
auto clip_pipeline_descriptor = solid_fill_pipeline->GetDescriptor();
28+
clip_pipeline_descriptor.SetLabel("Clip Pipeline");
2629
// Write to the stencil buffer.
2730
StencilAttachmentDescriptor stencil0;
2831
stencil0.stencil_compare = CompareFunction::kGreaterEqual;

impeller/entity/content_context.h

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -111,14 +111,16 @@ class ContentContext {
111111
return found->second->WaitAndGet();
112112
}
113113

114-
auto found = container.find({});
114+
auto prototype = container.find({});
115115

116116
// The prototype must always be initialized in the constructor.
117-
FML_CHECK(found != container.end());
117+
FML_CHECK(prototype != container.end());
118118

119-
auto variant_future = found->second->WaitAndGet()->CreateVariant(
120-
[&opts](PipelineDescriptor& desc) {
119+
auto variant_future = prototype->second->WaitAndGet()->CreateVariant(
120+
[&opts, variants_count = container.size()](PipelineDescriptor& desc) {
121121
ApplyOptionsToDescriptor(desc, opts);
122+
desc.SetLabel(
123+
SPrintF("%s V#%zu", desc.GetLabel().c_str(), variants_count));
122124
});
123125
auto variant = std::make_unique<TypedPipeline>(std::move(variant_future));
124126
auto variant_pipeline = variant->WaitAndGet();

impeller/renderer/backend/metal/pipeline_library_mtl.h

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -26,18 +26,16 @@ class PipelineLibraryMTL final : public PipelineLibrary {
2626
private:
2727
friend ContextMTL;
2828

29-
using Pipelines = std::unordered_map<PipelineDescriptor,
30-
std::shared_ptr<const Pipeline>,
31-
ComparableHash<PipelineDescriptor>,
32-
ComparableEqual<PipelineDescriptor>>;
29+
using Pipelines =
30+
std::unordered_map<PipelineDescriptor,
31+
std::shared_future<std::shared_ptr<Pipeline>>,
32+
ComparableHash<PipelineDescriptor>,
33+
ComparableEqual<PipelineDescriptor>>;
3334
id<MTLDevice> device_ = nullptr;
3435
Pipelines pipelines_;
3536

3637
PipelineLibraryMTL(id<MTLDevice> device);
3738

38-
void SavePipeline(PipelineDescriptor descriptor,
39-
std::shared_ptr<const Pipeline> pipeline);
40-
4139
// |PipelineLibrary|
4240
PipelineFuture GetRenderPipeline(PipelineDescriptor descriptor) override;
4341

impeller/renderer/backend/metal/pipeline_library_mtl.mm

Lines changed: 7 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -67,19 +67,16 @@
6767
return [device newDepthStencilStateWithDescriptor:descriptor];
6868
}
6969

70-
std::future<std::shared_ptr<Pipeline>> PipelineLibraryMTL::GetRenderPipeline(
70+
PipelineFuture PipelineLibraryMTL::GetRenderPipeline(
7171
PipelineDescriptor descriptor) {
72-
auto promise = std::make_shared<std::promise<std::shared_ptr<Pipeline>>>();
73-
auto future = promise->get_future();
7472
if (auto found = pipelines_.find(descriptor); found != pipelines_.end()) {
75-
promise->set_value(nullptr);
76-
return future;
73+
return found->second;
7774
}
7875

79-
// TODO(csg): There is a bug here where multiple calls to GetRenderPipeline
80-
// will result in multiple render pipelines of the same descriptor being
81-
// created till the first instance of the creation invokes its completion
82-
// callback.
76+
auto promise = std::make_shared<std::promise<std::shared_ptr<Pipeline>>>();
77+
auto future = PipelineFuture{promise->get_future()};
78+
79+
pipelines_[descriptor] = future;
8380

8481
auto weak_this = weak_from_this();
8582

@@ -100,25 +97,19 @@
10097
promise->set_value(nullptr);
10198
return;
10299
}
100+
103101
auto new_pipeline = std::shared_ptr<PipelineMTL>(new PipelineMTL(
104102
weak_this,
105103
descriptor, //
106104
render_pipeline_state, //
107105
CreateDepthStencilDescriptor(descriptor, device_) //
108106
));
109107
promise->set_value(new_pipeline);
110-
this->SavePipeline(descriptor, new_pipeline);
111108
};
112109
[device_ newRenderPipelineStateWithDescriptor:GetMTLRenderPipelineDescriptor(
113110
descriptor)
114111
completionHandler:completion_handler];
115112
return future;
116113
}
117114

118-
void PipelineLibraryMTL::SavePipeline(
119-
PipelineDescriptor descriptor,
120-
std::shared_ptr<const Pipeline> pipeline) {
121-
pipelines_[descriptor] = std::move(pipeline);
122-
}
123-
124115
} // namespace impeller

impeller/renderer/pipeline.h

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ class Pipeline;
2121
// would be a concurrency pessimization.
2222
//
2323
// Use a struct that stores the future and the descriptor separately.
24-
using PipelineFuture = std::future<std::shared_ptr<Pipeline>>;
24+
using PipelineFuture = std::shared_future<std::shared_ptr<Pipeline>>;
2525

2626
//------------------------------------------------------------------------------
2727
/// @brief Describes the fixed function and programmable aspects of
@@ -48,6 +48,13 @@ class Pipeline {
4848

4949
virtual bool IsValid() const = 0;
5050

51+
//----------------------------------------------------------------------------
52+
/// @brief Get the descriptor that was responsible for creating this
53+
/// pipeline. It may be copied and modified to create a pipeline
54+
/// variant.
55+
///
56+
/// @return The descriptor.
57+
///
5158
const PipelineDescriptor& GetDescriptor() const;
5259

5360
PipelineFuture CreateVariant(

0 commit comments

Comments
 (0)