[PATCH] winegcc: fix cross linking on multiarch platforms
Andre Heider
a.heider at gmail.com
Tue Nov 20 09:38:17 CST 2018
On 20/11/2018 14:38, Jacek Caban wrote:
> On 11/20/18 2:24 PM, Andre Heider wrote:
>> Hi,
>>
>> On 20/11/2018 13:53, Jacek Caban wrote:
>>> Hi Andre,
>>>
>>> On 11/20/18 1:10 PM, Andre Heider wrote:
>>>> If e.g. the 64bit libdir was set to /foo/lib/x86_64-linux-gnu/bar,
>>>> winegcc
>>>> will now look for the 32bit libdir at /foo/lib/i386-linux-gnu/bar.
>>>>
>>>> Signed-off-by: Andre Heider <a.heider at gmail.com>
>>>> ---
>>>> Tested on non-standard prefixes like /opt/foo as well as more exotic
>>>> variations like Debian's wine-development package, which uses
>>>> /usr/lib/x86_64-linux-gnu/wine-development
>>>> and
>>>> /usr/lib/i386-linux-gnu/wine-development
>>>>
>>>> tools/winegcc/winegcc.c | 40 ++++++++++++++++++++++++++++++----------
>>>> 1 file changed, 30 insertions(+), 10 deletions(-)
>>>>
>>>> diff --git a/tools/winegcc/winegcc.c b/tools/winegcc/winegcc.c
>>>> index 6b3b4b6aab..d463d7a4bf 100644
>>>> --- a/tools/winegcc/winegcc.c
>>>> +++ b/tools/winegcc/winegcc.c
>>>> @@ -444,6 +444,21 @@ static int check_platform( struct options
>>>> *opts, const char *file )
>>>> return ret;
>>>> }
>>>> +static const char *get_multiarch_dir( enum target_cpu cpu )
>>>> +{
>>>> + switch(cpu)
>>>> + {
>>>> + case CPU_x86: return "/i386-linux-gnu";
>>>> + case CPU_x86_64: return "/x86_64-linux-gnu";
>>>> + case CPU_ARM: return "/arm-linux-gnueabi";
>>>> + case CPU_ARM64: return "/aarch64-linux-gnu";
>>>> + case CPU_POWERPC: return "/powerpc-linux-gnu";
>>>> + default:
>>>> + assert(0);
>>>> + return NULL;
>>>> + }
>>>> +}
>>>> +
>>>> static char *get_lib_dir( struct options *opts )
>>>> {
>>>> static const char *stdlibpath[] = { LIBDIR, "/usr/lib",
>>>> "/usr/local/lib", "/lib" };
>>>> @@ -471,19 +486,24 @@ static char *get_lib_dir( struct options *opts )
>>>> strcpy( p, bit_suffix );
>>>> strcat( p, libwine );
>>>> if (check_platform( opts, buffer )) goto found;
>>>> - switch(opts->target_cpu)
>>>> - {
>>>> - case CPU_x86: strcpy( p, "/i386-linux-gnu" ); break;
>>>> - case CPU_x86_64: strcpy( p, "/x86_64-linux-gnu" ); break;
>>>> - case CPU_ARM: strcpy( p, "/arm-linux-gnueabi" ); break;
>>>> - case CPU_ARM64: strcpy( p, "/aarch64-linux-gnu" ); break;
>>>> - case CPU_POWERPC: strcpy( p, "/powerpc-linux-gnu" ); break;
>>>> - default:
>>>> - assert(0);
>>>> - }
>>>> + strcpy( p, get_multiarch_dir( opts->target_cpu ));
>>>> strcat( p, libwine );
>>>> if (check_platform( opts, buffer )) goto found;
>>>> + /* try s/$build_cpu/$target_cpu/ on multiarch */
>>>> + if (build_cpu != opts->target_cpu && (p = strstr(
>>>> stdlibpath[i], get_multiarch_dir( build_cpu ) )))
>>>> + {
>>>> + char *suffix = p + strlen( get_multiarch_dir( build_cpu
>>>> ) );
>>>> + strcpy( buffer, stdlibpath[i] );
>>>> + p = buffer + (p - stdlibpath[i]);
>>>> + strcpy( p, get_multiarch_dir( opts->target_cpu ) );
>>>> + p += strlen( get_multiarch_dir( opts->target_cpu ) );
>>>> + strcpy( p, suffix );
>>>> + while (p > buffer && p[-1] == '/') p--;
>>>> + strcat( p, libwine );
>>>> + if (check_platform( opts, buffer )) goto found;
>>>> + }
>>>
>>>
>>> It seems to me that extending the existing loop that tries to replace
>>> lib* path components would be better (it's the loop just a few lines
>>> bellow the code that you modify).
>>
>> Sure, I can do that, but doesn't that go against the idea of multiarch?
>>
>> If your distro uses /lib/$triple it shouldn't use /lib[32|64]/$triple
>> - at least I've never seen such a setup.
>>
>> Or would that solve the issue on a setup I didn't yet encounter?
>
>
> We would try to change that in this case only if $triple heuristic
> doesn't work. Instead of using strstr, there is a loop that tries to
> replace one component at the time. So if you build with -m32 on 64-bit
> host on a distro that uses an exotic /usr/lib/$triple/lib64/subdir
> libdir, we'd do following in the loop:
>
> - skip subdir
>
> - try to replace lib64 with lib32 or lib, if that fails
>
> - try to replace $triple with 32-bit triple, if that fails
>
> - try to replace lib with lib32, if that fails
>
> - skip usr
>
> - if we got here, we didn't find valid 32-bit libdir
>
>
> Does that make sense?
Oh, okay. Yeah, it does. I thought you meant all permutations. I tried
to avoid that memmove() block down there, but I'll give it a spin ;)
Thanks,
Andre
More information about the wine-devel
mailing list