1 //
2 // Copyright 2020 The ANGLE Project Authors. All rights reserved.
3 // Use of this source code is governed by a BSD-style license that can be
4 // found in the LICENSE file.
5 //
6 
7 #ifndef COMPILER_TRANSLATOR_TRANSLATORMETALDIRECT_PIPELINE_H_
8 #define COMPILER_TRANSLATOR_TRANSLATORMETALDIRECT_PIPELINE_H_
9 
10 #include "compiler/translator/Symbol.h"
11 #include "compiler/translator/TranslatorMetalDirect/ModifyStruct.h"
12 #include "compiler/translator/TranslatorMetalDirect/Name.h"
13 #include "compiler/translator/TranslatorMetalDirect/SymbolEnv.h"
14 
15 namespace sh
16 {
17 
18 // Data that is scoped as `external` and `internal` for a given pipeline.
19 template <typename T>
20 struct PipelineScoped
21 {
22     // Data that is configured to talk externally to the program.
23     // May coincide with `internal`, but may also diverge from `internal`.
24     const T *external = nullptr;
25 
26     // Data that is configured to talk internally within the program.
27     // May coincide with `external`, but may also diverge from `external`.
28     const T *internal = nullptr;
29 
30     // Returns true iff the input coincides with either `external` or `internal` data.
matchesPipelineScoped31     bool matches(const T &object) const { return external == &object || internal == &object; }
32 
33     // Both `external` and `internal` representations are non-null.
isTotallyFullPipelineScoped34     bool isTotallyFull() const { return external && internal; }
35 
36     // Both `external` and `internal` representations are null.
isTotallyEmptyPipelineScoped37     bool isTotallyEmpty() const { return !external && !internal; }
38 
39     // Both `external` and `internal` representations are the same.
isUniformPipelineScoped40     bool isUniform() const { return external == internal; }
41 };
42 
43 // Represents a high-level program pipeline.
44 class Pipeline
45 {
46   public:
47     enum class Type
48     {
49         VertexIn,
50         VertexOut,
51         FragmentIn,
52         FragmentOut,
53         UserUniforms,
54         AngleUniforms,
55         NonConstantGlobals,
56         InvocationVertexGlobals,
57         InvocationFragmentGlobals,
58         UniformBuffer,
59         Texture,
60         InstanceId,
61     };
62 
63     enum class Variant
64     {
65         // For all internal pipeline uses.
66         // For external pipeline uses if pipeline does not require splitting or saturation.
67         Original,
68 
69         // Only for external pipeline uses if the pipeline was split or saturated.
70         Modified,
71     };
72 
73   public:
74     // The type of the pipeline.
75     Type type;
76 
77     // Non-null if a global instance of the pipeline struct already exists.
78     // If non-null struct splitting should not be needed.
79     const TVariable *globalInstanceVar;
80 
81   public:
82     // Returns true iff the variable belongs to the pipeline.
83     bool uses(const TVariable &var) const;
84 
85     // Returns the name for the struct type that stores variables of this pipeline.
86     Name getStructTypeName(Variant variant) const;
87 
88     // Returns the name for the struct instance that stores variables of this pipeline.
89     Name getStructInstanceName(Variant variant) const;
90 
91     ModifyStructConfig externalStructModifyConfig() const;
92 
93     // Returns true if the pipeline always requires a non-parameter local instance declaration of
94     // the pipeline structures.
95     bool alwaysRequiresLocalVariableDeclarationInMain() const;
96 
97     // Returns true iff the pipeline is an output pipeline. The external pipeline structure should
98     // be returned from `main`.
99     bool isPipelineOut() const;
100 
101     AddressSpace externalAddressSpace() const;
102 };
103 
104 // A collection of various pipeline structures.
105 struct PipelineStructs : angle::NonCopyable
106 {
107     PipelineScoped<TStructure> fragmentIn;
108     PipelineScoped<TStructure> fragmentOut;
109     PipelineScoped<TStructure> vertexIn;
110     PipelineScoped<TStructure> vertexOut;
111     PipelineScoped<TStructure> userUniforms;
112     PipelineScoped<TStructure> angleUniforms;
113     PipelineScoped<TStructure> nonConstantGlobals;
114     PipelineScoped<TStructure> invocationVertexGlobals;
115     PipelineScoped<TStructure> invocationFragmentGlobals;
116     PipelineScoped<TStructure> uniformBuffers;
117     PipelineScoped<TStructure> texture;
118     PipelineScoped<TStructure> instanceId;
119 
120     bool matches(const TStructure &s, bool internal, bool external) const;
121 };
122 
123 }  // namespace sh
124 
125 #endif  // COMPILER_TRANSLATOR_TRANSLATORMETALDIRECT_PIPELINE_H_
126