1
0
forked from 0ad/0ad

Fix cpuid call with -fPIC on i386 architectures.

GCC < 5 used to reserve the ebx register for PIC (position-independent
code) metadata. This meant that we needed to save the state of ebx
before calling cpuid (fixed in #2675)
However, the original patch from 03eaf9b461 did not force a particular
register to store this value in. Following the GCC 5 upgrade, GCC
stopped reserving ebx, and that register silently got used instead. The
code became non-sensical, and our ASM __cpuidex started returning random
garbage in edx.

Since we now only support GCC7 and above, the PIC-specific branch is no
longer necessary and is removed.

Fixes #6028. The assertion was a result of random data in ebx.
Refs #2675 / reverts 6334ee3f8b and reverts 03eaf9b461.

Patch by: nwtour
Comments by: vladislavbelov
Differential Revision: https://code.wildfiregames.com/D3575
This was SVN commit r25405.
This commit is contained in:
wraitii 2021-05-09 12:41:45 +00:00
parent 1e1af6e2df
commit abb124a36f

View File

@ -1,4 +1,4 @@
/* Copyright (C) 2018 Wildfire Games.
/* Copyright (C) 2021 Wildfire Games.
*
* Permission is hereby granted, free of charge, to any person obtaining
* a copy of this software and associated documentation files (the
@ -49,20 +49,10 @@ namespace x86_x64 {
#if defined(_MSC_FULL_VER) && _MSC_FULL_VER >= 150030729
// VC10+ and VC9 SP1: __cpuidex is already available
#elif GCC_VERSION
# if defined(__i386__) && defined(__PIC__)
# define __cpuidex(regsArray, level, index)\
__asm__ __volatile__ ("pushl %%ebx\n"\
"cpuid\n"\
"mov %%ebx,%1\n"\
"popl %%ebx"\
: "=a" ((regsArray)[0]), "=r" ((regsArray)[1]), "=c" ((regsArray)[2]), "=d" ((regsArray)[3])\
: "0" (level), "2" (index));
# else
# define __cpuidex(regsArray, level, index)\
__asm__ __volatile__ ("cpuid"\
: "=a" ((regsArray)[0]), "=b" ((regsArray)[1]), "=c" ((regsArray)[2]), "=d" ((regsArray)[3])\
: "0" (level), "2" (index));
# endif
#else
# error "compiler not supported"
#endif