SHOW:
|
|
- or go back to the newest paste.
1 | diff --git a/dlls/wined3d/buffer.c b/dlls/wined3d/buffer.c | |
2 | index c53021b..5b4ef8e 100644 | |
3 | --- a/dlls/wined3d/buffer.c | |
4 | +++ b/dlls/wined3d/buffer.c | |
5 | @@ -1147,7 +1147,7 @@ static HRESULT buffer_init(struct wined3d_buffer *buffer, struct wined3d_device | |
6 | ||
7 | hr = resource_init(&buffer->resource, device, WINED3D_RTYPE_BUFFER, format, | |
8 | WINED3D_MULTISAMPLE_NONE, 0, usage, pool, size, 1, 1, size, | |
9 | - parent, parent_ops, &buffer_resource_ops); | |
10 | + parent, parent_ops, &buffer_resource_ops, 0); | |
11 | if (FAILED(hr)) | |
12 | { | |
13 | WARN("Failed to initialize resource, hr %#x\n", hr); | |
14 | diff --git a/dlls/wined3d/resource.c b/dlls/wined3d/resource.c | |
15 | index 177d23e..21b4c0d 100644 | |
16 | --- a/dlls/wined3d/resource.c | |
17 | +++ b/dlls/wined3d/resource.c | |
18 | @@ -82,7 +82,7 @@ HRESULT resource_init(struct wined3d_resource *resource, struct wined3d_device * | |
19 | enum wined3d_multisample_type multisample_type, UINT multisample_quality, | |
20 | DWORD usage, enum wined3d_pool pool, UINT width, UINT height, UINT depth, UINT size, | |
21 | void *parent, const struct wined3d_parent_ops *parent_ops, | |
22 | - const struct wined3d_resource_ops *resource_ops) | |
23 | + const struct wined3d_resource_ops *resource_ops, void *have_alloc) | |
24 | { | |
25 | const struct wined3d *d3d = device->wined3d; | |
26 | ||
27 | @@ -120,7 +120,9 @@ HRESULT resource_init(struct wined3d_resource *resource, struct wined3d_device * | |
28 | ||
29 | if (size) | |
30 | { | |
31 | - if (!wined3d_resource_allocate_sysmem(resource)) | |
32 | + if (have_alloc) { | |
33 | + resource->heap_memory = have_alloc; | |
34 | + } else if (!wined3d_resource_allocate_sysmem(resource)) | |
35 | { | |
36 | ERR("Failed to allocate system memory.\n"); | |
37 | return E_OUTOFMEMORY; | |
38 | diff --git a/dlls/wined3d/surface.c b/dlls/wined3d/surface.c | |
39 | index 628a4a5..3ab9878 100644 | |
40 | --- a/dlls/wined3d/surface.c | |
41 | +++ b/dlls/wined3d/surface.c | |
42 | @@ -6307,7 +6307,7 @@ cpu: | |
43 | } | |
44 | ||
45 | static HRESULT surface_init(struct wined3d_surface *surface, struct wined3d_texture *container, | |
46 | - const struct wined3d_resource_desc *desc, DWORD flags) | |
47 | + const struct wined3d_resource_desc *desc, DWORD flags, void *have_alloc) | |
48 | { | |
49 | struct wined3d_device *device = container->resource.device; | |
50 | const struct wined3d_gl_info *gl_info = &device->adapter->gl_info; | |
51 | @@ -6365,7 +6365,7 @@ static HRESULT surface_init(struct wined3d_surface *surface, struct wined3d_text | |
52 | ||
53 | if (FAILED(hr = resource_init(&surface->resource, device, WINED3D_RTYPE_SURFACE, format, | |
54 | desc->multisample_type, multisample_quality, desc->usage, desc->pool, desc->width, desc->height, 1, | |
55 | - resource_size, NULL, &wined3d_null_parent_ops, &surface_resource_ops))) | |
56 | + resource_size, NULL, &wined3d_null_parent_ops, &surface_resource_ops, have_alloc))) | |
57 | { | |
58 | WARN("Failed to initialize resource, returning %#x.\n", hr); | |
59 | return hr; | |
60 | @@ -6415,7 +6415,7 @@ static HRESULT surface_init(struct wined3d_surface *surface, struct wined3d_text | |
61 | } | |
62 | ||
63 | HRESULT CDECL wined3d_surface_create(struct wined3d_texture *container, | |
64 | - const struct wined3d_resource_desc *desc, DWORD flags, struct wined3d_surface **surface) | |
65 | + const struct wined3d_resource_desc *desc, DWORD flags, struct wined3d_surface **surface, void *have_alloc) | |
66 | { | |
67 | struct wined3d_device_parent *device_parent = container->resource.device->device_parent; | |
68 | const struct wined3d_parent_ops *parent_ops; | |
69 | @@ -6432,7 +6432,7 @@ HRESULT CDECL wined3d_surface_create(struct wined3d_texture *container, | |
70 | if (!(object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object)))) | |
71 | return E_OUTOFMEMORY; | |
72 | ||
73 | - if (FAILED(hr = surface_init(object, container, desc, flags))) | |
74 | + if (FAILED(hr = surface_init(object, container, desc, flags, have_alloc))) | |
75 | { | |
76 | WARN("Failed to initialize surface, returning %#x.\n", hr); | |
77 | HeapFree(GetProcessHeap(), 0, object); | |
78 | diff --git a/dlls/wined3d/texture.c b/dlls/wined3d/texture.c | |
79 | index 897af19..cb03c4c 100644 | |
80 | --- a/dlls/wined3d/texture.c | |
81 | +++ b/dlls/wined3d/texture.c | |
82 | @@ -51,7 +51,7 @@ static HRESULT wined3d_texture_init(struct wined3d_texture *texture, const struc | |
83 | ||
84 | if (FAILED(hr = resource_init(&texture->resource, device, desc->resource_type, format, | |
85 | desc->multisample_type, desc->multisample_quality, desc->usage, desc->pool, | |
86 | - desc->width, desc->height, desc->depth, 0, parent, parent_ops, resource_ops))) | |
87 | + desc->width, desc->height, desc->depth, 0, parent, parent_ops, resource_ops, 0))) | |
88 | { | |
89 | WARN("Failed to initialize resource, returning %#x\n", hr); | |
90 | return hr; | |
91 | @@ -879,7 +879,7 @@ static HRESULT cubetexture_init(struct wined3d_texture *texture, const struct wi | |
92 | UINT idx = j * texture->level_count + i; | |
93 | struct wined3d_surface *surface; | |
94 | ||
95 | - if (FAILED(hr = wined3d_surface_create(texture, &surface_desc, surface_flags, &surface))) | |
96 | + if (FAILED(hr = wined3d_surface_create(texture, &surface_desc, surface_flags, &surface, 0))) | |
97 | { | |
98 | WARN("Failed to create surface, hr %#x.\n", hr); | |
99 | wined3d_texture_cleanup(texture); | |
100 | @@ -897,6 +897,21 @@ static HRESULT cubetexture_init(struct wined3d_texture *texture, const struct wi | |
101 | return WINED3D_OK; | |
102 | } | |
103 | ||
104 | +void* wined3d_resource_allocate_sysmem_from_size(SIZE_T size) | |
105 | +{ | |
106 | + void **p; | |
107 | + SIZE_T align = RESOURCE_ALIGNMENT - 1 + sizeof(*p); | |
108 | + void *mem; | |
109 | + | |
110 | + if (!(mem = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, size + align))) | |
111 | + return FALSE; | |
112 | + | |
113 | + p = (void **)(((ULONG_PTR)mem + align) & ~(RESOURCE_ALIGNMENT - 1)) - 1; | |
114 | + *p = mem; | |
115 | + | |
116 | + return ++p; | |
117 | +} | |
118 | + | |
119 | static HRESULT texture_init(struct wined3d_texture *texture, const struct wined3d_resource_desc *desc, | |
120 | UINT levels, DWORD surface_flags, struct wined3d_device *device, void *parent, | |
121 | const struct wined3d_parent_ops *parent_ops) | |
122 | @@ -1029,25 +1044,42 @@ static HRESULT texture_init(struct wined3d_texture *texture, const struct wined3 | |
123 | /* Generate all the surfaces. */ | |
124 | surface_desc = *desc; | |
125 | surface_desc.resource_type = WINED3D_RTYPE_SURFACE; | |
126 | + | |
127 | + SIZE_T resource_size = 0; | |
128 | + UINT pw = surface_desc.width; | |
129 | + UINT ph = surface_desc.height; | |
130 | + const struct wined3d_format *format = wined3d_get_format(gl_info, desc->format); | |
131 | + // compute the needed space for all mipmaps | |
132 | + for (i = 0; i < texture->level_count; ++i) | |
133 | + { | |
134 | + resource_size += wined3d_format_calculate_size(format, device->surface_alignment, pw, ph, 1); | |
135 | + // next mipmap | |
136 | + pw = max(1, pw >> 1); | |
137 | + ph = max(1, ph >> 1); | |
138 | + } | |
139 | + // alloc | |
140 | + void *base_surface_alloc = wined3d_resource_allocate_sysmem_from_size(resource_size); | |
141 | + void *last_alloc = base_surface_alloc; | |
142 | for (i = 0; i < texture->level_count; ++i) | |
143 | { | |
144 | struct wined3d_surface *surface; | |
145 | ||
146 | - if (FAILED(hr = wined3d_surface_create(texture, &surface_desc, surface_flags, &surface))) | |
147 | + if (FAILED(hr = wined3d_surface_create(texture, &surface_desc, surface_flags, &surface, last_alloc))) | |
148 | { | |
149 | WARN("Failed to create surface, hr %#x.\n", hr); | |
150 | wined3d_texture_cleanup(texture); | |
151 | return hr; | |
152 | } | |
153 | + last_alloc += wined3d_format_calculate_size(format, device->surface_alignment, surface_desc.width, surface_desc.height, 1); | |
154 | ||
155 | surface_set_texture_target(surface, texture->target, i); | |
156 | texture->sub_resources[i] = &surface->resource; | |
157 | + | |
158 | TRACE("Created surface level %u @ %p.\n", i, surface); | |
159 | /* Calculate the next mipmap level. */ | |
160 | surface_desc.width = max(1, surface_desc.width >> 1); | |
161 | surface_desc.height = max(1, surface_desc.height >> 1); | |
162 | } | |
163 | - | |
164 | return WINED3D_OK; | |
165 | } | |
166 | ||
167 | diff --git a/dlls/wined3d/volume.c b/dlls/wined3d/volume.c | |
168 | index 817fe7e..335c65e 100644 | |
169 | --- a/dlls/wined3d/volume.c | |
170 | +++ b/dlls/wined3d/volume.c | |
171 | @@ -839,7 +839,7 @@ static HRESULT volume_init(struct wined3d_volume *volume, struct wined3d_texture | |
172 | ||
173 | if (FAILED(hr = resource_init(&volume->resource, device, WINED3D_RTYPE_VOLUME, format, | |
174 | WINED3D_MULTISAMPLE_NONE, 0, desc->usage, desc->pool, desc->width, desc->height, desc->depth, | |
175 | - size, NULL, &wined3d_null_parent_ops, &volume_resource_ops))) | |
176 | + size, NULL, &wined3d_null_parent_ops, &volume_resource_ops, 0))) | |
177 | { | |
178 | WARN("Failed to initialize resource, returning %#x.\n", hr); | |
179 | return hr; | |
180 | diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h | |
181 | index 991db87..853a6c3 100644 | |
182 | --- a/dlls/wined3d/wined3d_private.h | |
183 | +++ b/dlls/wined3d/wined3d_private.h | |
184 | @@ -2015,7 +2015,7 @@ HRESULT resource_init(struct wined3d_resource *resource, struct wined3d_device * | |
185 | enum wined3d_multisample_type multisample_type, UINT multisample_quality, | |
186 | DWORD usage, enum wined3d_pool pool, UINT width, UINT height, UINT depth, UINT size, | |
187 | void *parent, const struct wined3d_parent_ops *parent_ops, | |
188 | - const struct wined3d_resource_ops *resource_ops) DECLSPEC_HIDDEN; | |
189 | + const struct wined3d_resource_ops *resource_ops, void *have_alloc) DECLSPEC_HIDDEN; | |
190 | DWORD resource_set_priority(struct wined3d_resource *resource, DWORD priority) DECLSPEC_HIDDEN; | |
191 | void resource_unload(struct wined3d_resource *resource) DECLSPEC_HIDDEN; | |
192 | BOOL wined3d_resource_allocate_sysmem(struct wined3d_resource *resource) DECLSPEC_HIDDEN; | |
193 | @@ -2275,7 +2275,7 @@ HRESULT surface_upload_from_surface(struct wined3d_surface *dst_surface, const P | |
194 | struct wined3d_surface *src_surface, const RECT *src_rect) DECLSPEC_HIDDEN; | |
195 | void surface_validate_location(struct wined3d_surface *surface, DWORD location) DECLSPEC_HIDDEN; | |
196 | HRESULT CDECL wined3d_surface_create(struct wined3d_texture *container, | |
197 | - const struct wined3d_resource_desc *desc, DWORD flags, struct wined3d_surface **surface) DECLSPEC_HIDDEN; | |
198 | + const struct wined3d_resource_desc *desc, DWORD flags, struct wined3d_surface **surface, void *last_alloc) DECLSPEC_HIDDEN; | |
199 | void surface_prepare_map_memory(struct wined3d_surface *surface) DECLSPEC_HIDDEN; | |
200 | ||
201 | void get_drawable_size_swapchain(const struct wined3d_context *context, UINT *width, UINT *height) DECLSPEC_HIDDEN; |