Commit 1bcc7ce7 authored by Henri Verbeet's avatar Henri Verbeet Committed by Alexandre Julliard

d3d10: Validate offsets and size in parse_fx10_type() (AFL).

parent 7f6520a2
...@@ -598,11 +598,18 @@ static D3D10_SHADER_VARIABLE_TYPE d3d10_variable_type(DWORD t, BOOL is_object) ...@@ -598,11 +598,18 @@ static D3D10_SHADER_VARIABLE_TYPE d3d10_variable_type(DWORD t, BOOL is_object)
static HRESULT parse_fx10_type(const char *data, size_t data_size, DWORD offset, struct d3d10_effect_type *t) static HRESULT parse_fx10_type(const char *data, size_t data_size, DWORD offset, struct d3d10_effect_type *t)
{ {
const char *ptr = data + offset; const char *ptr;
DWORD unknown0; DWORD unknown0;
DWORD typeinfo; DWORD typeinfo;
unsigned int i; unsigned int i;
if (offset >= data_size || !require_space(offset, 6, sizeof(DWORD), data_size))
{
WARN("Invalid offset %#x (data size %#lx).\n", offset, (long)data_size);
return E_FAIL;
}
ptr = data + offset;
read_dword(&ptr, &offset); read_dword(&ptr, &offset);
TRACE("Type name at offset %#x.\n", offset); TRACE("Type name at offset %#x.\n", offset);
...@@ -631,9 +638,14 @@ static HRESULT parse_fx10_type(const char *data, size_t data_size, DWORD offset, ...@@ -631,9 +638,14 @@ static HRESULT parse_fx10_type(const char *data, size_t data_size, DWORD offset,
switch (unknown0) switch (unknown0)
{ {
case 1: case 1:
t->member_count = 0; if (!require_space(ptr - data, 1, sizeof(typeinfo), data_size))
{
WARN("Invalid offset %#x (data size %#lx).\n", offset, (long)data_size);
return E_FAIL;
}
read_dword(&ptr, &typeinfo); read_dword(&ptr, &typeinfo);
t->member_count = 0;
t->column_count = (typeinfo & D3D10_FX10_TYPE_COLUMN_MASK) >> D3D10_FX10_TYPE_COLUMN_SHIFT; t->column_count = (typeinfo & D3D10_FX10_TYPE_COLUMN_MASK) >> D3D10_FX10_TYPE_COLUMN_SHIFT;
t->row_count = (typeinfo & D3D10_FX10_TYPE_ROW_MASK) >> D3D10_FX10_TYPE_ROW_SHIFT; t->row_count = (typeinfo & D3D10_FX10_TYPE_ROW_MASK) >> D3D10_FX10_TYPE_ROW_SHIFT;
t->basetype = d3d10_variable_type((typeinfo & D3D10_FX10_TYPE_BASETYPE_MASK) >> D3D10_FX10_TYPE_BASETYPE_SHIFT, FALSE); t->basetype = d3d10_variable_type((typeinfo & D3D10_FX10_TYPE_BASETYPE_MASK) >> D3D10_FX10_TYPE_BASETYPE_SHIFT, FALSE);
...@@ -651,13 +663,18 @@ static HRESULT parse_fx10_type(const char *data, size_t data_size, DWORD offset, ...@@ -651,13 +663,18 @@ static HRESULT parse_fx10_type(const char *data, size_t data_size, DWORD offset,
case 2: case 2:
TRACE("Type is an object.\n"); TRACE("Type is an object.\n");
if (!require_space(ptr - data, 1, sizeof(typeinfo), data_size))
{
WARN("Invalid offset %#x (data size %#lx).\n", offset, (long)data_size);
return E_FAIL;
}
read_dword(&ptr, &typeinfo);
t->member_count = 0; t->member_count = 0;
t->column_count = 0; t->column_count = 0;
t->row_count = 0; t->row_count = 0;
t->type_class = D3D10_SVC_OBJECT;
read_dword(&ptr, &typeinfo);
t->basetype = d3d10_variable_type(typeinfo, TRUE); t->basetype = d3d10_variable_type(typeinfo, TRUE);
t->type_class = D3D10_SVC_OBJECT;
TRACE("Type description: %#x.\n", typeinfo); TRACE("Type description: %#x.\n", typeinfo);
TRACE("\tbasetype: %s.\n", debug_d3d10_shader_variable_type(t->basetype)); TRACE("\tbasetype: %s.\n", debug_d3d10_shader_variable_type(t->basetype));
...@@ -667,6 +684,12 @@ static HRESULT parse_fx10_type(const char *data, size_t data_size, DWORD offset, ...@@ -667,6 +684,12 @@ static HRESULT parse_fx10_type(const char *data, size_t data_size, DWORD offset,
case 3: case 3:
TRACE("Type is a structure.\n"); TRACE("Type is a structure.\n");
if (!require_space(ptr - data, 1, sizeof(t->member_count), data_size))
{
WARN("Invalid offset %#x (data size %#lx).\n", offset, (long)data_size);
return E_FAIL;
}
read_dword(&ptr, &t->member_count); read_dword(&ptr, &t->member_count);
TRACE("Member count: %u.\n", t->member_count); TRACE("Member count: %u.\n", t->member_count);
...@@ -681,6 +704,13 @@ static HRESULT parse_fx10_type(const char *data, size_t data_size, DWORD offset, ...@@ -681,6 +704,13 @@ static HRESULT parse_fx10_type(const char *data, size_t data_size, DWORD offset,
return E_OUTOFMEMORY; return E_OUTOFMEMORY;
} }
if (!require_space(ptr - data, t->member_count, 4 * sizeof(DWORD), data_size))
{
WARN("Invalid member count %#x (data size %#lx, offset %#x).\n",
t->member_count, (long)data_size, offset);
return E_FAIL;
}
for (i = 0; i < t->member_count; ++i) for (i = 0; i < t->member_count; ++i)
{ {
struct d3d10_effect_type_member *typem = &t->members[i]; struct d3d10_effect_type_member *typem = &t->members[i];
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment