1 /*
2 * Copyright (c) 2019, 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 //! \file     mos_cmdbufmgr_next.h
24 //! \brief    Container class for the comamnd buffer manager
25 //!
26 
27 #ifndef __COMMAND_BUFFER_MANAGER_NEXT_H__
28 #define __COMMAND_BUFFER_MANAGER_NEXT_H__
29 
30 #include "mos_commandbuffer_next.h"
31 #include "mos_gpucontextmgr_next.h"
32 
33 //!
34 //! \class  CmdBufMgr
35 //!
36 class CmdBufMgrNext
37 {
38 public:
39     //!
40     //! \brief  Constructor
41     //!
42     CmdBufMgrNext();
43 
44     //!
45     //! \brief  Destructor
46     //!
47     ~CmdBufMgrNext();
48 
49     //!
50     //! \brief    Static entrypoint, get command buffer manager object
51     //! \return   CmdBufMgrNext*
52     //!           comamnd buffer manager object if success, else nullptr
53     //!
54     static CmdBufMgrNext* GetObject();
55 
56     //!
57     //! \brief    Initialize comamnd buffer manager object
58     //! \details  This function mainly create initial cmd buffer as input size
59     //! \param    [in] osContext
60     //!           Pointer to the osContext handle
61     //! \param    [in] cmdBufSize
62     //!           initialized command buffer size
63     //! \return   MOS_STATUS
64     //!           MOS_STATUS_SUCCESS if success, else fail reason
65     //!
66     MOS_STATUS Initialize(OsContextNext *osContext, uint32_t cmdBufSize);
67 
68     //!
69     //! \brief    Clean up the command buffer manager
70     //! \details  This function mainly celar all allocated comamnd buffer in
71     //!           available pool and in use pool
72     //!
73     void CleanUp();
74 
75     //!
76     //! \brief    Clean up the command buffer manager
77     //! \details  This function will pick up one proper command buffer from
78     //!           available pool, internal logic in below 3 conditions:
79     //!           1: if available pool has command buffer and its size bigger than
80     //!              required, directly put it into in use pool and return;
81     //!           2: if available pool has command buffer but size smaller than
82     //!              required, only create one command buffer as reqired and put
83     //!              it to in  use pool directly;
84     //!           3: if available pool is empty, will re-allocate bunch of command
85     //!              buffers, buffer number base on m_initBufNum, buffer size
86     //!              base on input required size. After re-allocate, put first buf
87     //!              into inuse pool, remains push to available pool.
88     //! \param    [in] size
89     //!           Required command buffer size
90     //! \return   CommandBuffer*
91     //!           Proper comamnd bufffer pointer if success, other wise nullptr
92     //!
93     CommandBufferNext *PickupOneCmdBuf(uint32_t size);
94 
95     //!
96     //! \brief    insert the command buffer into available pool in proper location.
97     //! \details  This function will find a the first cmd buffer which equal or
98     //!           small cmd buf size in available pool, and then insert it.
99     //! \param    [in] cmdBuf
100     //!           command buffer to be released
101     //!
102     void UpperInsert(CommandBufferNext *cmdBuf);
103 
104     //!
105     //! \brief    Release command buffer from in-use status to standby status
106     //! \details  This function designed for situations which need retire or
107     //!           discard in use command buffer, it directly erase command buf
108     //!           from in use pool and push it to available pool. If the command
109     //!           buffer cannot be found inside in-use pool, some thing must be
110     //!           wrong.
111     //! \param    [in] cmdBuf
112     //!           Command buffer need to be released
113     //! \return   MOS_STATUS
114     //!           MOS_STATUS_SUCCESS if success, other wise fail reason
115     //!
116     MOS_STATUS ReleaseCmdBuf(CommandBufferNext *cmdBuf);
117 
118     //!
119     //! \brief    Reset the command buffer to the initial state
120     //! \details  This function designed for situations where the command buffer manager
121     //!           is reused for another context. It unbind all command buffers from the
122     //!           gpucontext and recycle all the command buffers in use.
123     //! \return   MOS_STATUS
124     //!           MOS_STATUS_SUCCESS if success, other wise fail reason
125     //!
126     MOS_STATUS Reset();
127 
128     //!
129     //! \brief    Resize command buffer with required size
130     //! \param    [in] cmdBufToResize
131     //!           Command buffer need to be resized
132     //! \param    [in] newSize
133     //!           required new size
134     //! \return   MOS_STATUS
135     //!           MOS_STATUS_SUCCESS if success, other wise fail reason
136     //!
137     MOS_STATUS ResizeOneCmdBuf(CommandBufferNext *cmdBufToResize, uint32_t newSize);
138 
139     //!
140     //! \brief    Get the validity flag
141     //! \return   bool
142     //!           Get the validity flag of cmdBufMgrNext
143     //!
IsInitialized()144     bool IsInitialized()
145     {
146         return m_initialized;
147     }
148 
149     //!
150     //! \brief    Set the cmd buf mgr handle
151     //! \return   MOS_STATUS
152     //!           MOS_STATUS_SUCCESS if success, other wise fail reason
153     //!
SetCmdBufMgrHandle(uint64_t handle)154     MOS_STATUS SetCmdBufMgrHandle(uint64_t handle)
155     {
156         m_handle = handle;
157         return MOS_STATUS_SUCCESS;
158     }
159 
160     //!
161     //! \brief    Get the cmd buf mgr handle
162     //! \return   uint64_t
163     //!           Get the handle of cmdBufMgrNext
164     //!
GetCmdBufMgrHandle()165     uint64_t GetCmdBufMgrHandle()
166     {
167         return m_handle;
168     }
169 
170  protected:
171     //!
172     //! \brief    Self define compare method as std:sort input
173     //! \detail   Command buffer size will be compared
174     //! \param    [in] a
175     //!           Input command buffer to be compared
176     //! \param    [in] b
177     //!           Input command buffer to be compared
178     //! \return   bool
179     //!           true if a size bigger than b, otherwise false
180     //!
181     static bool GreaterSizeSort(CommandBufferNext *a, CommandBufferNext *b);
182 
183     //! \brief   Max comamnd buffer number for per manager, including all
184     //!          command buffer in availble pool and in-use pool
185     constexpr static uint32_t m_maxPoolSize = 1098304;
186 
187     //! \brief   Current command buffer number in available and in-use pool
188     uint32_t m_cmdBufTotalNum = 0;
189 
190     //! \brief   Command buffer number when bunch of re-allocate
191     constexpr static uint32_t m_bufIncStepSize = 8;
192 
193     //! \brief   Initial command buffer number
194     constexpr static uint32_t m_initBufNum = 32;
195 
196     //! \brief   Sorted List of available command buffer pool
197     std::vector<CommandBufferNext *> m_availableCmdBufPool;
198 
199     //! \brief   Mutex for available command buffer pool
200     PMOS_MUTEX m_availablePoolMutex = nullptr;
201 
202     //! \brief   List of in used command buffer pool
203     std::vector<CommandBufferNext *> m_inUseCmdBufPool;
204 
205     //! \brief   Mutex for in-use command buffer pool
206     PMOS_MUTEX m_inUsePoolMutex = nullptr;
207 
208     //! \brief   Flag to indicate cmd buf mgr initialized or not
209     bool m_initialized = false;
210 
211     //! \brief   Corresponding os context
212     OsContextNext *m_osContext = nullptr;
213 
214     //! \brief   cmd buffer handle
215     uint64_t       m_handle     = 0;
216 };
217 #endif // __COMMAND_BUFFER_MANAGER_NEXT_H__
218