xref: /aosp_15_r20/external/mesa3d/src/gallium/winsys/svga/drm/vmw_screen_pools.c (revision 6104692788411f58d303aa86923a9ff6ecaded22)
1 /*
2  * Copyright (c) 2009-2024 Broadcom. All Rights Reserved.
3  * The term “Broadcom” refers to Broadcom Inc.
4  * and/or its subsidiaries.
5  * SPDX-License-Identifier: MIT
6  */
7 
8 
9 #include "vmw_screen.h"
10 
11 #include "vmw_buffer.h"
12 #include "vmw_fence.h"
13 
14 #include "pipebuffer/pb_buffer.h"
15 #include "pipebuffer/pb_bufmgr.h"
16 
17 /**
18  * vmw_pools_cleanup - Destroy the buffer pools.
19  *
20  * @vws: pointer to a struct vmw_winsys_screen.
21  */
22 void
vmw_pools_cleanup(struct vmw_winsys_screen * vws)23 vmw_pools_cleanup(struct vmw_winsys_screen *vws)
24 {
25    if (vws->pools.dma_slab_fenced)
26       vws->pools.dma_slab_fenced->destroy
27          (vws->pools.dma_slab_fenced);
28    if (vws->pools.dma_slab)
29       vws->pools.dma_slab->destroy(vws->pools.dma_slab);
30    if (vws->pools.dma_fenced)
31       vws->pools.dma_fenced->destroy(vws->pools.dma_fenced);
32    if (vws->pools.dma_cache)
33       vws->pools.dma_cache->destroy(vws->pools.dma_cache);
34 
35    if (vws->pools.query_fenced)
36       vws->pools.query_fenced->destroy(vws->pools.query_fenced);
37    if (vws->pools.query_mm)
38       vws->pools.query_mm->destroy(vws->pools.query_mm);
39 
40    if (vws->pools.dma_mm)
41       vws->pools.dma_mm->destroy(vws->pools.dma_mm);
42    if (vws->pools.dma_base)
43       vws->pools.dma_base->destroy(vws->pools.dma_base);
44 }
45 
46 
47 /**
48  * vmw_query_pools_init - Create a pool of query buffers.
49  *
50  * @vws: Pointer to a struct vmw_winsys_screen.
51  *
52  * Typically this pool should be created on demand when we
53  * detect that the app will be using queries. There's nothing
54  * special with this pool other than the backing kernel buffer sizes,
55  * which are limited to 8192.
56  * If there is a performance issue with allocation and freeing of the
57  * query slabs, it should be easily fixable by allocating them out
58  * of a buffer cache.
59  */
60 bool
vmw_query_pools_init(struct vmw_winsys_screen * vws)61 vmw_query_pools_init(struct vmw_winsys_screen *vws)
62 {
63    struct pb_desc desc;
64 
65    desc.alignment = 16;
66    desc.usage = ~(VMW_BUFFER_USAGE_SHARED | VMW_BUFFER_USAGE_SYNC);
67 
68    vws->pools.query_mm = pb_slab_range_manager_create(vws->pools.dma_base, 16, 128,
69                                                       VMW_QUERY_POOL_SIZE,
70                                                       &desc);
71    if (!vws->pools.query_mm)
72       return false;
73 
74    vws->pools.query_fenced = simple_fenced_bufmgr_create(
75       vws->pools.query_mm, vws->fence_ops);
76 
77    if(!vws->pools.query_fenced)
78       goto out_no_query_fenced;
79 
80    return true;
81 
82   out_no_query_fenced:
83    vws->pools.query_mm->destroy(vws->pools.query_mm);
84    return false;
85 }
86 
87 /**
88  * vmw_pool_init - Create a pool of buffers.
89  *
90  * @vws: Pointer to a struct vmw_winsys_screen.
91  */
92 bool
vmw_pools_init(struct vmw_winsys_screen * vws)93 vmw_pools_init(struct vmw_winsys_screen *vws)
94 {
95    struct pb_desc desc;
96 
97    vws->pools.dma_base = vmw_dma_bufmgr_create(vws);
98    if (!vws->pools.dma_base)
99       goto error;
100 
101    /*
102     * A managed pool for DMA buffers.
103     */
104    vws->pools.dma_mm = mm_bufmgr_create(vws->pools.dma_base,
105                                         VMW_GMR_POOL_SIZE,
106                                         12 /* 4096 alignment */);
107    if(!vws->pools.dma_mm)
108       goto error;
109 
110    vws->pools.dma_cache =
111       pb_cache_manager_create(vws->pools.dma_base, 100000, 2.0f,
112                               VMW_BUFFER_USAGE_SHARED,
113                               64 * 1024 * 1024);
114 
115    if (!vws->pools.dma_cache)
116       goto error;
117 
118    vws->pools.dma_fenced =
119       simple_fenced_bufmgr_create(vws->pools.dma_cache,
120                                   vws->fence_ops);
121 
122    if(!vws->pools.dma_fenced)
123       goto error;
124 
125    /*
126     * The slab pool allocates buffers directly from the kernel except
127     * for very small buffers which are allocated from a slab in order
128     * not to waste memory, since a kernel buffer is a minimum 4096 bytes.
129     *
130     * Here we use it only for emergency in the case our pre-allocated
131     * managed buffer pool runs out of memory.
132     */
133    desc.alignment = 64;
134    desc.usage = ~(SVGA_BUFFER_USAGE_PINNED | VMW_BUFFER_USAGE_SHARED |
135                   VMW_BUFFER_USAGE_SYNC);
136    vws->pools.dma_slab =
137       pb_slab_range_manager_create(vws->pools.dma_cache,
138                                    64,
139                                    8192,
140                                    16384,
141                                    &desc);
142    if(!vws->pools.dma_slab)
143      goto error;
144 
145    vws->pools.dma_slab_fenced =
146       simple_fenced_bufmgr_create(vws->pools.dma_slab,
147 		                  vws->fence_ops);
148    if (!vws->pools.dma_slab_fenced)
149       goto error;
150 
151    vws->pools.query_fenced = NULL;
152    vws->pools.query_mm = NULL;
153 
154    return true;
155 
156 error:
157    vmw_pools_cleanup(vws);
158    return false;
159 }
160