1 /*
2 * Copyright (c) 2018-2021, Intel Corporation
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice shall be included
12 * in all copies or substantial portions of the Software.
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
15 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
17 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
18 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
19 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
20 * OTHER DEALINGS IN THE SOFTWARE.
21 */
22 
23 //!
24 //! \file     media_context.h
25 //! \brief    Defines the common interface for media context
26 //! \details  The media context interface is further sub-divided by component,
27 //!           this file is for the base interface which is shared by all components.
28 //!
29 
30 #ifndef __MEDIA_CONTEXT_H__
31 #define __MEDIA_CONTEXT_H__
32 
33 #include "mos_os.h"
34 #include "media_scalability_factory.h"
35 
36 struct _MHW_VDBOX_GPUNODE_LIMIT;
37 typedef struct _MHW_VDBOX_GPUNODE_LIMIT MHW_VDBOX_GPUNODE_LIMIT, *PMHW_VDBOX_GPUNODE_LIMIT;
38 
39 enum MediaFunction
40 {
41     RenderGenericFunc,
42     VdboxDecodeFunc,
43     VdboxEncodeFunc,
44     VdboxCpFunc,
45     VeboxVppFunc,
46     ComputeMdfFunc,
47     ComputeVppFunc,
48     VdboxDecodeWaFunc,
49     VdboxDecrpytFunc,
50     VdboxDecodeVirtualNode0Func,
51     VdboxDecodeVirtualNode1Func,
52     MediaFuncMax
53 };
54 // Be compatible to legacy MOS and re-define the name
55 #define INVALID_MEDIA_FUNCTION MediaFuncMax
56 #define IS_RENDER_ENGINE_FUNCTION(func) ( func == RenderGenericFunc || func == ComputeMdfFunc || func == ComputeVppFunc )
57 
58 struct GpuContextAttribute
59 {
60     MediaFunction      func                = INVALID_MEDIA_FUNCTION;
61     MediaScalability * scalabilityState    = nullptr;
62 
63     MOS_GPU_CONTEXT    ctxForLegacyMos     = MOS_GPU_CONTEXT_MAX;
64     GPU_CONTEXT_HANDLE gpuContext          = MOS_GPU_CONTEXT_INVALID_HANDLE;
65 };
66 
67 class MediaContext
68 {
69 public:
70     //!
71     //! \brief  Media context constructor
72     //!
73     MediaContext(uint8_t componentType, void *hwInterface, PMOS_INTERFACE osInterface);
74 
75     //!
76     //! \brief  Media context destructor
77     //!
78     virtual ~MediaContext();
79 
80     //!
81     //! \brief  Interface to pipeline to switch media context and get corresponding scalabilityState for programming
82     //! \param  [in] func
83     //!         Indicate the media function of the context to switch
84     //! \param  [in] requirement
85     //!         Pointer to the context requirement
86     //! \param  [out] scalabilityState
87     //!         Pointer to the pointer of output scalability state.
88     //!         Pipeline can only use this scalabilityState until next time calling SwitchContext
89     //! \return MOS_STATUS
90     //!         MOS_STATUS_SUCCESS if success, else fail reason
91     //!
92     MOS_STATUS SwitchContext(MediaFunction func, ContextRequirement *requirement, MediaScalability **scalabilityState);
93 
94     //!
95     //! \brief  Interface to pipeline to switch media context and get corresponding scalabilityState for programming
96     //! \param  [in] func
97     //!         Indicate the media function of the context to switch
98     //! \param  [in] scalabilityOption
99     //!         The intialzed scalability option
100     //! \param  [out] scalabilityState
101     //!         Pointer to the pointer of output scalability state.
102     //!         Pipeline can only use this scalabilityState until next time calling SwitchContext
103     //! \param  [in] isEnc
104     //!         Indicate if this is Enc stage
105     //! \param  [in] isPak
106     //!         Indicate if this is Pak stage
107     //! \return MOS_STATUS
108     //!         MOS_STATUS_SUCCESS if success, else fail reason
109     //!
110     MOS_STATUS SwitchContext(MediaFunction func, MediaScalabilityOption &scalabilityOption, MediaScalability **scalabilityState,
111                              bool isEnc = false, bool isPak = false);
112 
113     //!
114     //! \brief  Check if in current media context render engine is used
115     //! \return bool
116     //!         True if render engine used, else false.
117     //!
IsRenderEngineUsed()118     bool IsRenderEngineUsed()
119     {
120         auto gpuContext = m_osInterface->pfnGetGpuContext(m_osInterface);
121         // Be compatiable to legacy MOS
122         return MOS_RCS_ENGINE_USED(gpuContext);
123     }
124 
GetNumVdbox()125     uint8_t GetNumVdbox()
126     {
127         m_numVdbox                      = 1;
128         MEDIA_SYSTEM_INFO *gtSystemInfo = m_osInterface->pfnGetGtSystemInfo(m_osInterface);
129         if (gtSystemInfo != nullptr)
130         {
131             // Both VE mode and media solo mode should be able to get the VDBOX number via the same interface
132             m_numVdbox = (uint8_t)(gtSystemInfo->VDBoxInfo.NumberOfVDBoxEnabled);
133         }
134         return m_numVdbox;
135     }
136 
137     //!
138     //! \brief  Set latest decoder virtual node
139     //!
140     void SetLatestDecoderVirtualNode();
141 
142     //!
143     //! \brief  Reassgine virtual node for decoder
144     //! \param  [in] frameNum
145     //!         The current decoding frame number
146     //! \param  [in] scalabilityOption
147     //!         The intialzed scalability option
148     //! \param  [out] scalabilityState
149     //!         Pointer to the pointer of output scalability state.
150     //!         Pipeline can only use this scalabilityState until next time calling SwitchContext
151     //! \return MOS_STATUS
152     //!         MOS_STATUS_SUCCESS if success, else fail reason
153     //!
154     MOS_STATUS ReassignContextForDecoder(uint32_t frameNum, MediaScalabilityOption &scalabilityOption, MediaScalability **scalabilityState);
155 
156     //!
157     //! \brief  Reassgine virtual node for decoder
158     //! \param  [in] frameNum
159     //!         The current decoding frame number
160     //! \param  [in] scalabilityOption
161     //!         The intialzed scalability option
162     //! \param  [out] scalabilityState
163     //!         Pointer to the pointer of output scalability state.
164     //!         Pipeline can only use this scalabilityState until next time calling SwitchContext
165     //! \return MOS_STATUS
166     //!         MOS_STATUS_SUCCESS if success, else fail reason
167     //!
168     MOS_STATUS ReassignContextForDecoder(uint32_t frameNum, ContextRequirement *requirement, MediaScalability **scalabilityState);
169 
170 protected:
171     PMOS_INTERFACE                    m_osInterface             = nullptr;           //!< OS interface
172     void                             *m_hwInterface             = nullptr;           //!< HW interface
173     uint8_t                           m_componentType           = scalabilityTotal;  //!< Media component
174     uint32_t                          m_streamId                = m_invalidStreamId; //!< Stream id of this media context
175 
176     std::vector<GpuContextAttribute>  m_gpuContextAttributeTable;                    //!< Gpu Context Attribute Table to store the contexts to reuse
177 
178     static const uint32_t             m_invalidContextAttribute = 0xffffffdf;        //!< Index value to indicate invalid Context Attribute
179     static const uint32_t             m_invalidStreamId         = 0xffffffcb;        //!< Id to indicate invalid Stream
180     static const uint32_t             m_maxContextAttribute     = 4096;              //!< Max number of entries supported in gpuContextAttributeTable in one media context
181     uint8_t                           m_numVdbox                = 1;
182     bool                              m_scalabilitySupported    = false;
183     MOS_GPU_NODE                      m_curNodeOrdinal          = MOS_GPU_NODE_MAX;  //!< Current virtual node for codec gpu context
184     MediaUserSettingSharedPtr         m_userSettingPtr          = nullptr;           //!< Shared pointer to user setting instance
185 
186     //!
187     //! \brief  Search the ContextAttributeTable to reuse or create gpu Context and scalabilty state meeting the requirements
188     //! \param  [in] func
189     //!         Indicate the media function of the context
190     //! \param  [in] params
191     //!         The params for context searching
192     //! \param  [out] indexFound
193     //!         The index of the ContextAttributeTable which is found to match the requirements
194     //! \return MOS_STATUS
195     //!         MOS_STATUS_SUCCESS if success, else fail reason
196     //!
197     template<typename T>
198     MOS_STATUS SearchContext(MediaFunction func, T params, uint32_t& indexFound);
199 
200     //!
201     //! \brief  Creat the context for new requirement
202     //! \param  [in] func
203     //!         Indicate the media function of the context
204     //! \param  [in] params
205     //!         Pointer to the context requirement
206     //! \param  [out] indexReturn
207     //!         Return index for new ContextAttributeTable
208     //! \return MOS_STATUS
209     //!         MOS_STATUS_SUCCESS if success, else fail reason
210     //!
211     template<typename T>
212     MOS_STATUS CreateContext(MediaFunction func, T params, uint32_t& indexReturn);
213 
214     //!
215     //! \brief  Get the GPU node of the Media Function
216     //! \detail Usually there is a corresponding GPU node to implement the specific media function
217     //! \param  [in] func
218     //!         Media function to get GPU node
219     //! \param  [in] option
220     //!         Media GPU create option
221     //! \param  [out] node
222     //!         GPU node of the media function
223     //! \return MOS_STATUS
224     //!         MOS_STATUS_SUCCESS if success, else fail reason
225     //!
226     MOS_STATUS FunctionToNode(MediaFunction func, const MOS_GPUCTX_CREATOPTIONS_ENHANCED &option, MOS_GPU_NODE& node);
227     MOS_STATUS FunctionToNodeCodec(MediaFunction func, MOS_GPU_NODE &node);
228     MOS_STATUS FindGpuNodeToUse(MediaFunction func, PMHW_VDBOX_GPUNODE_LIMIT gpuNodeLimit);
229 
230     // Be compatible to Legacy MOS
231     MOS_STATUS FunctionToGpuContext(MediaFunction func, const MOS_GPUCTX_CREATOPTIONS_ENHANCED &option, const MOS_GPU_NODE &node, MOS_GPU_CONTEXT &ctx);
232     MOS_STATUS FunctionToGpuContextDecode(const MOS_GPUCTX_CREATOPTIONS_ENHANCED &option, const MOS_GPU_NODE &node, MOS_GPU_CONTEXT &ctx);
233     MOS_STATUS FunctionToGpuContextEncode(const MOS_GPUCTX_CREATOPTIONS_ENHANCED &option, MOS_GPU_CONTEXT &ctx);
234 
235     #if (_DEBUG || _RELEASE_INTERNAL)
236     MOS_STATUS CheckScalabilityOverrideValidity();
237     #endif
238 
239 MEDIA_CLASS_DEFINE_END(MediaContext)
240 };
241 #endif  // !__MEDIA_CONTEXT_H__
242