RegEnumValue[AW] need to update the data size on buffer overflow (spotted by Massimo <max@veneto.com>).
diff --git a/dlls/advapi32/registry.c b/dlls/advapi32/registry.c index a9cddb8..61858af 100644 --- a/dlls/advapi32/registry.c +++ b/dlls/advapi32/registry.c
@@ -1076,7 +1076,7 @@ if (info->NameLength/sizeof(WCHAR) >= *val_count) { status = STATUS_BUFFER_OVERFLOW; - goto done; + goto overflow; } memcpy( value, info->Name, info->NameLength ); *val_count = info->NameLength / sizeof(WCHAR); @@ -1088,7 +1088,7 @@ if (total_size - info->DataOffset > *count) { status = STATUS_BUFFER_OVERFLOW; - goto done; + goto overflow; } memcpy( data, buf_ptr + info->DataOffset, total_size - info->DataOffset ); if (total_size - info->DataOffset <= *count-sizeof(WCHAR) && is_string(info->Type)) @@ -1102,6 +1102,7 @@ } else status = STATUS_SUCCESS; + overflow: if (type) *type = info->Type; if (count) *count = info->DataLength; @@ -1154,21 +1155,6 @@ if (status) goto done; - if (value) - { - DWORD len; - - RtlUnicodeToMultiByteSize( &len, info->Name, info->NameLength ); - if (len >= *val_count) - { - status = STATUS_BUFFER_OVERFLOW; - goto done; - } - RtlUnicodeToMultiByteN( value, len, NULL, info->Name, info->NameLength ); - value[len] = 0; - *val_count = len; - } - if (is_string(info->Type)) { DWORD len; @@ -1176,16 +1162,15 @@ total_size - info->DataOffset ); if (data && len) { - if (len > *count) + if (len > *count) status = STATUS_BUFFER_OVERFLOW; + else { - status = STATUS_BUFFER_OVERFLOW; - goto done; + RtlUnicodeToMultiByteN( data, len, NULL, (WCHAR *)(buf_ptr + info->DataOffset), + total_size - info->DataOffset ); + /* if the type is REG_SZ and data is not 0-terminated + * and there is enough space in the buffer NT appends a \0 */ + if (len < *count && data[len-1]) data[len] = 0; } - RtlUnicodeToMultiByteN( data, len, NULL, (WCHAR *)(buf_ptr + info->DataOffset), - total_size - info->DataOffset ); - /* if the type is REG_SZ and data is not 0-terminated - * and there is enough space in the buffer NT appends a \0 */ - if (len < *count && data[len-1]) data[len] = 0; } info->DataLength = len; } @@ -1194,6 +1179,29 @@ if (total_size - info->DataOffset > *count) status = STATUS_BUFFER_OVERFLOW; else memcpy( data, buf_ptr + info->DataOffset, total_size - info->DataOffset ); } + + if (value && !status) + { + DWORD len; + + RtlUnicodeToMultiByteSize( &len, info->Name, info->NameLength ); + if (len >= *val_count) + { + status = STATUS_BUFFER_OVERFLOW; + if (*val_count) + { + len = *val_count - 1; + RtlUnicodeToMultiByteN( value, len, NULL, info->Name, info->NameLength ); + value[len] = 0; + } + } + else + { + RtlUnicodeToMultiByteN( value, len, NULL, info->Name, info->NameLength ); + value[len] = 0; + *val_count = len; + } + } } else status = STATUS_SUCCESS;