mirror of
https://github.com/clearlinux/linux-steam-integration.git
synced 2026-09-07 14:21:48 +00:00
Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
6137c52bab | ||
|
|
524810bbd2 | ||
|
|
d7006fdb74 | ||
|
|
211ac7613c | ||
|
|
5352b5deab | ||
|
|
54bd49281c | ||
|
|
8b09218039 | ||
|
|
89e7b7cfbb | ||
|
|
ffe7825f62 | ||
|
|
0f24683688 | ||
|
|
abcb5feeaf | ||
|
|
6963c34892 | ||
|
|
8d9aac19f6 | ||
|
|
c4ded16115 | ||
|
|
6bc12dde6e | ||
|
|
8968b69788 | ||
|
|
6a5fff703c | ||
|
|
11e9ff2137 | ||
|
|
05343c140f | ||
|
|
c03d5cdff8 | ||
|
|
4c68fcc7d7 | ||
|
|
09c84f0866 | ||
|
|
fc9ae2e9c2 | ||
|
|
9624bde1b9 | ||
|
|
a951a49910 | ||
|
|
fc88ee1496 | ||
|
|
ae48c61932 | ||
|
|
fb56eca35d | ||
|
|
1c3a39ebfa | ||
|
|
62cf7443ac | ||
|
|
46c423d065 | ||
|
|
c34938a43a | ||
|
|
62bd3dffb7 | ||
|
|
5c809fdc07 | ||
|
|
e7eae9d577 | ||
|
|
a1c2235120 | ||
|
|
5b59075ec0 | ||
|
|
c640f2f215 | ||
|
|
b80f79c8d0 | ||
|
|
851f354f9f | ||
|
|
10d3be6a38 | ||
|
|
c8a45b7303 | ||
|
|
1b932e94fa |
@@ -5,7 +5,7 @@ Linux Steam* Integration is a helper system to make the Steam Client and Steam
|
|||||||
games run better on Linux. In a nutshell, LSI automatically applies various workarounds
|
games run better on Linux. In a nutshell, LSI automatically applies various workarounds
|
||||||
to get games working, and fixes long standing bugs in both games and the client.
|
to get games working, and fixes long standing bugs in both games and the client.
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
In many cases this will involve controlling which libraries are allowed to be used
|
In many cases this will involve controlling which libraries are allowed to be used
|
||||||
at any given time, and these libraries may be overriden for any of the following
|
at any given time, and these libraries may be overriden for any of the following
|
||||||
@@ -15,12 +15,12 @@ reasons:
|
|||||||
- Compatibility
|
- Compatibility
|
||||||
- Performance
|
- Performance
|
||||||
|
|
||||||
|
This project, and by extension the platforms it runs on, are not officially endorsed by, or affiliated with, Steam, or its parent company, Valve*.
|
||||||
|
This fork of linux-steam-integration is now being maintained separately from the original project, to suit the cadence and requirements of the
|
||||||
|
Clear Linux* Project for Intel Architecture.
|
||||||
|
|
||||||
This project, and by extension Solus, is not officially endorsed by, or affiliated with, Steam, or its parent company, Valve*.
|
This project will retain backwards compatibility with the original project at the time of forking to alleviate maintainer concerns, whilst focusing
|
||||||
|
on improvements to match a wider audience than the original project, and ensuring native runtimes continue to work unimpeded.
|
||||||
Linux Steam Integration is a [Solus project](https://solus-project.com/)
|
|
||||||
|
|
||||||

|
|
||||||
|
|
||||||
### Linking compatibility
|
### Linking compatibility
|
||||||
|
|
||||||
@@ -69,40 +69,14 @@ modules, `liblsi-redirect.so` and `liblsi-intercept.so`, to dynamically apply al
|
|||||||
workarounds at runtime, which in turn is set up by the main LSI `shim` binary.
|
workarounds at runtime, which in turn is set up by the main LSI `shim` binary.
|
||||||
|
|
||||||
For a more in depth view of what LSI is, and how to integrate it into your distribution,
|
For a more in depth view of what LSI is, and how to integrate it into your distribution,
|
||||||
please check the [technical README document](https://github.com/solus-project/linux-steam-integration/blob/master/TECHNICAL.md).
|
please check the [technical README document](https://github.com/clearlinux/linux-steam-integration/blob/master/TECHNICAL.md).
|
||||||
|
|
||||||
Be advised that we intend to remove the need for distributions to integrate LSI in the near future, by providing
|
|
||||||
the LSI system as a [snap](https://snapcraft.io/) package for all supported distributions.
|
|
||||||
|
|
||||||
## Getting LSI
|
|
||||||
|
|
||||||
LSI may not yet be available for your distribution, however some community maintained repositories do exist.
|
|
||||||
|
|
||||||
- [Arch Linux](https://aur.archlinux.org/packages/linux-steam-integration/)
|
|
||||||
- [Fedora](https://copr.fedorainfracloud.org/coprs/alunux/linux-steam-integration/)
|
|
||||||
- Solus uses LSI by default, just install the `steam` package.
|
|
||||||
|
|
||||||
To install the experimental snaps (`snapd` >= 2.29.4):
|
|
||||||
|
|
||||||
sudo snap install --edge solus-runtime-gaming
|
|
||||||
sudo snap install --devmode --edge solus-runtime-gaming
|
|
||||||
|
|
||||||
## Snap Support
|
|
||||||
|
|
||||||
LSI is currently undergoing work to become a universal package for all Linux distributions!
|
|
||||||
|
|
||||||
Items left to implement:
|
|
||||||
|
|
||||||
- [x] Add basic library support for snapd environment
|
|
||||||
- [x] Make `shim` support `$SNAP` style environmental variables for local Steam
|
|
||||||
- [x] Add support to LSI + `snapd` for NVIDIA+Vulkan
|
|
||||||
- [ ] Verify "normal" games work again
|
|
||||||
- [x] Publish snaps (edge)
|
|
||||||
|
|
||||||
|
|
||||||
## License
|
## License
|
||||||
|
|
||||||
Copyright © 2016-2017 Ikey Doherty
|
Copyright © 2016-2018 Ikey Doherty
|
||||||
|
|
||||||
|
Copyright © 2018-2019 Intel Corporation
|
||||||
|
|
||||||
linux-steam-integration is available under the terms of the `LGPL-2.1` license.
|
linux-steam-integration is available under the terms of the `LGPL-2.1` license.
|
||||||
|
|
||||||
|
|||||||
+2
-8
@@ -196,7 +196,7 @@ Currently this INI file supports three options. The root section in this INI fil
|
|||||||
`force-32bit = $boolean`
|
`force-32bit = $boolean`
|
||||||
|
|
||||||
If set to a true boolean value (yes/true/on), the shadowed Steam binary will
|
If set to a true boolean value (yes/true/on), the shadowed Steam binary will
|
||||||
be run via the `linux32` command. This will force the `steam` process
|
be run via the `setarch linux32` command. This will force the `steam` process
|
||||||
and all children to believe they are running on a 32-bit system. This
|
and all children to believe they are running on a 32-bit system. This
|
||||||
may be useful for 64-bit games that are buggy only on 64-bit.
|
may be useful for 64-bit games that are buggy only on 64-bit.
|
||||||
|
|
||||||
@@ -270,13 +270,7 @@ If you are noticing performance regressions, you can:
|
|||||||
- As a packager: Disable `liblsi-intercept` via build flags. This will hurt compatibility.
|
- As a packager: Disable `liblsi-intercept` via build flags. This will hurt compatibility.
|
||||||
- As a distribution integrator: Add weight to upstream issue and import patch into your distribution.
|
- As a distribution integrator: Add weight to upstream issue and import patch into your distribution.
|
||||||
This will retain LSI compatibility magic and mitigate performance issues.
|
This will retain LSI compatibility magic and mitigate performance issues.
|
||||||
As an example, Solus has already [integrated the patch](https://dev.solus-project.com/R927:afa5b639e8a9b62618457a304d1e6fb42a9f2066).
|
As an example, Solus has already [integrated the patch](https://dev.getsol.us/R927:afa5b639e8a9b62618457a304d1e6fb42a9f2066).
|
||||||
|
|
||||||
The long term solution is to remove this burden from non-Solus Linux distributions, and for the Solus & LSI projects to
|
|
||||||
provide a specialised runtime & strict LSI build via third party mechanisms so that all this work only needs doing once.
|
|
||||||
This will help ensure the same gaming experience regardless of Linux distribution, remove all compatibility issues, and
|
|
||||||
any pressures on distributions. Additionally this will allow even distributions not supporting multilib to provide a
|
|
||||||
curated and well integrated gaming runtime.
|
|
||||||
|
|
||||||
|
|
||||||
`* Some names may be claimed as the property of others.`
|
`* Some names may be claimed as the property of others.`
|
||||||
|
|||||||
@@ -0,0 +1,19 @@
|
|||||||
|
Initial test list for next release of LSI
|
||||||
|
|
||||||
|
- DOTA 2
|
||||||
|
- Don't Starve Together
|
||||||
|
- Requires curl-gnutls (integrating into CLR now)
|
||||||
|
- Vendored SDL is patched in non upstreamable fashion
|
||||||
|
https://forums.kleientertainment.com/forums/topic/30218-crash-on-linux-steam-without-error/?page=0&tab=comments#comment-386249
|
||||||
|
We'll need to allow certain games to vendor SDL now.
|
||||||
|
Fixed in https://github.com/clearlinux/linux-steam-integration/commit/c4ded161159d2d6faa5a1dba45af8426738632b7
|
||||||
|
- Oxygen Not Included (working perfectly)
|
||||||
|
- Cities:Skylines
|
||||||
|
- Various Source titles (L4D2, Portal, etc)
|
||||||
|
- Various Feral titles (2018/2019 kits)
|
||||||
|
- Stardew Valley
|
||||||
|
- Rocket League
|
||||||
|
|
||||||
|
+1 release:
|
||||||
|
|
||||||
|
- Proton compat
|
||||||
@@ -8,6 +8,7 @@ Type=Application
|
|||||||
Categories=Network;FileTransfer;Game;
|
Categories=Network;FileTransfer;Game;
|
||||||
MimeType=x-scheme-handler/steam;
|
MimeType=x-scheme-handler/steam;
|
||||||
Actions=Store;Community;Library;Servers;Screenshots;News;Settings;BigPicture;Friends;
|
Actions=Store;Community;Library;Servers;Screenshots;News;Settings;BigPicture;Friends;
|
||||||
|
StartupWMClass=Steam
|
||||||
|
|
||||||
[Desktop Action Store]
|
[Desktop Action Store]
|
||||||
Name=Store
|
Name=Store
|
||||||
|
|||||||
+3
-3
@@ -1,4 +1,4 @@
|
|||||||
appsdir = join_paths(datadir, 'applications')
|
path_appsdir = join_paths(path_datadir, 'applications')
|
||||||
|
|
||||||
# If frontend is enabled, install lsi-settings.desktop
|
# If frontend is enabled, install lsi-settings.desktop
|
||||||
if with_frontend == true
|
if with_frontend == true
|
||||||
@@ -12,7 +12,7 @@ if with_frontend == true
|
|||||||
input: 'lsi-settings.desktop.in',
|
input: 'lsi-settings.desktop.in',
|
||||||
output: 'lsi-settings.desktop',
|
output: 'lsi-settings.desktop',
|
||||||
configuration: data_conf,
|
configuration: data_conf,
|
||||||
install_dir: appsdir,
|
install_dir: path_appsdir,
|
||||||
)
|
)
|
||||||
endif
|
endif
|
||||||
|
|
||||||
@@ -20,6 +20,6 @@ endif
|
|||||||
if shim_behaviour == 'co-exist'
|
if shim_behaviour == 'co-exist'
|
||||||
install_data(
|
install_data(
|
||||||
'lsi-steam.desktop',
|
'lsi-steam.desktop',
|
||||||
install_dir: appsdir,
|
install_dir: path_appsdir,
|
||||||
)
|
)
|
||||||
endif
|
endif
|
||||||
|
|||||||
+86
-15
@@ -1,7 +1,7 @@
|
|||||||
project(
|
project(
|
||||||
'linux-steam-integration',
|
'linux-steam-integration',
|
||||||
['c'],
|
['c'],
|
||||||
version: '0.7',
|
version: '0.7.3',
|
||||||
license: [
|
license: [
|
||||||
'LGPL-2.1',
|
'LGPL-2.1',
|
||||||
],
|
],
|
||||||
@@ -10,7 +10,6 @@ project(
|
|||||||
],
|
],
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
am_cflags = [
|
am_cflags = [
|
||||||
'-fstack-protector',
|
'-fstack-protector',
|
||||||
'-pedantic',
|
'-pedantic',
|
||||||
@@ -33,69 +32,141 @@ add_global_arguments(am_cflags, language: 'c')
|
|||||||
|
|
||||||
dep_gtk3 = dependency('gtk+-3.0', version: '>= 3.4.0')
|
dep_gtk3 = dependency('gtk+-3.0', version: '>= 3.4.0')
|
||||||
|
|
||||||
|
# Grab all our main paths
|
||||||
|
path_prefix = get_option('prefix')
|
||||||
|
path_bindir = join_paths(path_prefix, get_option('bindir'))
|
||||||
|
path_datadir = join_paths(path_prefix, get_option('datadir'))
|
||||||
|
path_vendordir = join_paths(path_datadir, 'defaults', meson.project_name())
|
||||||
|
path_sysconfdir = join_paths(path_prefix, get_option('sysconfdir'))
|
||||||
|
path_localedir = join_paths(path_prefix, get_option('localedir'))
|
||||||
|
|
||||||
|
# Set up our basic configuration
|
||||||
cdata = configuration_data()
|
cdata = configuration_data()
|
||||||
|
|
||||||
cdata.set_quoted('PACKAGE_NAME', meson.project_name())
|
cdata.set_quoted('PACKAGE_NAME', meson.project_name())
|
||||||
|
cdata.set_quoted('SYSTEMCONFDIR', path_sysconfdir)
|
||||||
prefix = get_option('prefix')
|
cdata.set_quoted('VENDORDIR', path_vendordir)
|
||||||
datadir = join_paths(prefix, get_option('datadir'))
|
cdata.set_quoted('LOCALEDIR', path_localedir)
|
||||||
vendordir = join_paths(datadir, 'defaults', meson.project_name())
|
|
||||||
sysconfdir = join_paths(prefix, get_option('sysconfdir'))
|
|
||||||
localedir = join_paths(prefix, get_option('localedir'))
|
|
||||||
cdata.set_quoted('SYSTEMCONFDIR', sysconfdir)
|
|
||||||
cdata.set_quoted('VENDORDIR', vendordir)
|
|
||||||
cdata.set_quoted('LOCALEDIR', localedir)
|
|
||||||
cdata.set_quoted('GETTEXT_PACKAGE', meson.project_name())
|
cdata.set_quoted('GETTEXT_PACKAGE', meson.project_name())
|
||||||
|
|
||||||
# Configurables
|
# Configurables
|
||||||
cdata.set_quoted('LSI_PRELOAD_LIBS', get_option('with-preload-libs'))
|
with_preload_libs = get_option('with-preload-libs')
|
||||||
|
cdata.set_quoted('LSI_PRELOAD_LIBS', with_preload_libs)
|
||||||
cdata.set_quoted('STEAM_BINARY', get_option('with-steam-binary'))
|
cdata.set_quoted('STEAM_BINARY', get_option('with-steam-binary'))
|
||||||
|
|
||||||
|
# Future reports
|
||||||
|
shim_system_report = []
|
||||||
|
intercept_module_report = []
|
||||||
|
redirect_module_report = []
|
||||||
|
|
||||||
|
# Control the shim behaviour
|
||||||
shim_behaviour = get_option('with-shim')
|
shim_behaviour = get_option('with-shim')
|
||||||
|
shim_enabled = false
|
||||||
if shim_behaviour == 'replacement'
|
if shim_behaviour == 'replacement'
|
||||||
cdata.set('REPLACE_STEAM', '1')
|
cdata.set('REPLACE_STEAM', '1')
|
||||||
endif
|
endif
|
||||||
|
if shim_behaviour != 'none'
|
||||||
|
shim_enabled = true
|
||||||
|
endif
|
||||||
|
shim_system_report += ' behaviour: @0@'.format(shim_behaviour)
|
||||||
|
shim_system_report += ' preload libraries: @0@'.format(with_preload_libs)
|
||||||
|
|
||||||
|
# Do we have liblsi-intercept?
|
||||||
with_libintercept = get_option('with-libintercept')
|
with_libintercept = get_option('with-libintercept')
|
||||||
if with_libintercept == true
|
if with_libintercept == true
|
||||||
cdata.set('HAVE_LIBINTERCEPT', '1')
|
cdata.set('HAVE_LIBINTERCEPT', '1')
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
# Do we have liblsi-redirect?
|
||||||
with_libredirect = get_option('with-libredirect')
|
with_libredirect = get_option('with-libredirect')
|
||||||
if with_libredirect == true
|
if with_libredirect == true
|
||||||
cdata.set('HAVE_LIBREDIRECT', '1')
|
cdata.set('HAVE_LIBREDIRECT', '1')
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
# Do we have the frontend?
|
||||||
with_frontend = get_option('with-frontend')
|
with_frontend = get_option('with-frontend')
|
||||||
|
|
||||||
if get_option('with-new-libcxx-abi') == true
|
# Using the new libc++ ABI? Important for mesa drivers
|
||||||
|
with_new_libcxx_abi = get_option('with-new-libcxx-abi')
|
||||||
|
if with_new_libcxx_abi == true
|
||||||
cdata.set('LSI_USE_NEW_ABI', '1')
|
cdata.set('LSI_USE_NEW_ABI', '1')
|
||||||
endif
|
endif
|
||||||
|
shim_system_report += ' New C++ ABI: @0@'.format(with_new_libcxx_abi)
|
||||||
|
|
||||||
|
# How are we handling LibreSSL?
|
||||||
with_libressl_mode = get_option('with-libressl-mode')
|
with_libressl_mode = get_option('with-libressl-mode')
|
||||||
|
intercept_module_report += ' LibreSSL handling: @0@'.format(with_libressl_mode)
|
||||||
|
|
||||||
if with_libressl_mode == 'native'
|
if with_libressl_mode == 'native'
|
||||||
|
# LibreSSL is provided by the distro as the native libssl, libcrypto, etc
|
||||||
cdata.set('LSI_LIBRESSL_MODE_NATIVE', '1')
|
cdata.set('LSI_LIBRESSL_MODE_NATIVE', '1')
|
||||||
cdata.set('LSI_OVERRIDE_LIBRESSL', '1')
|
cdata.set('LSI_OVERRIDE_LIBRESSL', '1')
|
||||||
elif with_libressl_mode == 'shim'
|
elif with_libressl_mode == 'shim'
|
||||||
|
# A shim package has been provided for soname redirects to updated/secure libressl
|
||||||
|
# This allows distros to secure libressl without making it the system libssl/libcrypto option
|
||||||
cdata.set('LSI_LIBRESSL_MODE_SHIM', '1')
|
cdata.set('LSI_LIBRESSL_MODE_SHIM', '1')
|
||||||
cdata.set('LSI_OVERRIDE_LIBRESSL', '1')
|
cdata.set('LSI_OVERRIDE_LIBRESSL', '1')
|
||||||
cdata.set_quoted('LSI_LIBRESSL_SUFFIX', get_option('with-libressl-suffix'))
|
with_libressl_suffix = get_option('with-libressl-suffix')
|
||||||
|
intercept_module_report += ' LibreSSL library suffix: @0@'.format(with_libressl_suffix)
|
||||||
|
cdata.set_quoted('LSI_LIBRESSL_SUFFIX', with_libressl_suffix)
|
||||||
else
|
else
|
||||||
message('LibreSSL mode isn\'t configured which may impact security')
|
message('LibreSSL mode isn\'t configured which may impact security')
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
# Got snap support?
|
||||||
with_snap_support = get_option('with-snap-support')
|
with_snap_support = get_option('with-snap-support')
|
||||||
if with_snap_support == true
|
if with_snap_support == true
|
||||||
cdata.set('HAVE_SNAPD_SUPPORT', '1')
|
cdata.set('HAVE_SNAPD_SUPPORT', '1')
|
||||||
|
path_fake_scripts_dir = join_paths(path_datadir, meson.project_name(), 'scripts')
|
||||||
|
cdata.set_quoted('FAKE_SCRIPTS_DIR', path_fake_scripts_dir)
|
||||||
|
subdir('snapd')
|
||||||
message('Enabling snapd support. Do NOT do this for distribution builds!')
|
message('Enabling snapd support. Do NOT do this for distribution builds!')
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
# Let's write the global config.h now
|
||||||
config_h = configure_file(
|
config_h = configure_file(
|
||||||
configuration: cdata,
|
configuration: cdata,
|
||||||
output: 'config.h',
|
output: 'config.h',
|
||||||
)
|
)
|
||||||
|
# Make it discoverable
|
||||||
config_h_dir = include_directories('.')
|
config_h_dir = include_directories('.')
|
||||||
|
|
||||||
|
# Descend into source trees
|
||||||
subdir('data')
|
subdir('data')
|
||||||
subdir('src')
|
subdir('src')
|
||||||
subdir('po')
|
subdir('po')
|
||||||
|
|
||||||
|
report = [
|
||||||
|
' Build configuration:',
|
||||||
|
' ====================',
|
||||||
|
'',
|
||||||
|
' prefix: @0@'.format(path_prefix),
|
||||||
|
' datadir: @0@'.format(path_datadir),
|
||||||
|
' sysconfdir: @0@'.format(path_sysconfdir),
|
||||||
|
' bindir: @0@'.format(path_bindir),
|
||||||
|
'',
|
||||||
|
' Shim System (Execution/Environment Control):',
|
||||||
|
' ============================================',
|
||||||
|
'',
|
||||||
|
' enabled: @0@'.format(shim_enabled),
|
||||||
|
'@0@'.format('\n'.join(shim_system_report)),
|
||||||
|
'',
|
||||||
|
' Intercept Module (Dynamic Linker Control):',
|
||||||
|
' ==========================================',
|
||||||
|
'',
|
||||||
|
' enabled: @0@'.format(with_libintercept),
|
||||||
|
'@0@'.format('\n'.join(intercept_module_report)),
|
||||||
|
'',
|
||||||
|
' Redirect Module (Standard Library Control):',
|
||||||
|
' ===========================================',
|
||||||
|
'',
|
||||||
|
' enabled: @0@'.format(with_libredirect),
|
||||||
|
'',
|
||||||
|
' Snap Support (run as a snap):',
|
||||||
|
' =============================',
|
||||||
|
'',
|
||||||
|
' enabled: @0@'.format(with_snap_support),
|
||||||
|
'@0@'.format('\n'.join(redirect_module_report)),
|
||||||
|
]
|
||||||
|
|
||||||
|
# Output some stuff to validate the build config
|
||||||
|
message('\n\n\n' + '\n'.join(report) + '\n\n')
|
||||||
|
|||||||
+1
-1
@@ -3,7 +3,7 @@ option('with-shim', type : 'combo', choices : ['replacement', 'co-exist', 'none'
|
|||||||
option('with-steam-binary', type: 'string', description: 'Set the path to the Steam binary', value: '/usr/lib/steam/steam')
|
option('with-steam-binary', type: 'string', description: 'Set the path to the Steam binary', value: '/usr/lib/steam/steam')
|
||||||
option('with-frontend', type: 'boolean', description: 'Build the LSI Settings UI', value: false)
|
option('with-frontend', type: 'boolean', description: 'Build the LSI Settings UI', value: false)
|
||||||
option('with-preload-libs', type: 'string', description: 'Colon separated list of libraries required to launch Steam games',
|
option('with-preload-libs', type: 'string', description: 'Colon separated list of libraries required to launch Steam games',
|
||||||
value: '/usr/\$LIB/libxcb.so.1:/usr/\$LIB/libX11.so.6:/usr/\$LIB/libstdc++.so.6')
|
value: '/usr/$LIB/libxcb.so.1:/usr/$LIB/libX11.so.6:/usr/$LIB/libstdc++.so.6')
|
||||||
option('with-libintercept', type: 'boolean', description: 'Enable libintercept library for controlling Steam linking', value: true)
|
option('with-libintercept', type: 'boolean', description: 'Enable libintercept library for controlling Steam linking', value: true)
|
||||||
option('with-libredirect', type: 'boolean', description: 'Enable libredirect library for fine-tuning Steam games', value: true)
|
option('with-libredirect', type: 'boolean', description: 'Enable libredirect library for fine-tuning Steam games', value: true)
|
||||||
option('with-new-libcxx-abi', type: 'boolean', description: 'Enable when using the new libstdc++ ABI', value: false)
|
option('with-new-libcxx-abi', type: 'boolean', description: 'Enable when using the new libstdc++ ABI', value: false)
|
||||||
|
|||||||
+19
-2
@@ -1,12 +1,29 @@
|
|||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
set -e
|
set -e
|
||||||
|
|
||||||
|
DEFAULT_ARGS="-Dwith-libressl-mode=shim -Dwith-new-libcxx-abi=true"
|
||||||
|
|
||||||
if [[ ! -d buildroot/build32 ]]; then
|
if [[ ! -d buildroot/build32 ]]; then
|
||||||
CC="gcc -m32" linux32 meson buildroot/build32 -Dwith-libressl-mode=shim --prefix=/usr --sysconfdir=/etc --datadir=/usr/share --libdir=/usr/lib32 -Dwith-shim=none -Dwith-new-libcxx-abi=true --buildtype debugoptimized
|
ASFLAGS="$ASFLAGS --32" CFLAGS="$CFLAGS -m32" CXXFLAGS="$CXXFLAGS -m32" LDFLAGS="$LDFLAGS -m32" \
|
||||||
|
meson buildroot/build32 $DEFAULT_ARGS \
|
||||||
|
--prefix=/usr \
|
||||||
|
--sysconfdir=/etc \
|
||||||
|
--datadir=/usr/share \
|
||||||
|
--libdir=/usr/lib32 \
|
||||||
|
-Dwith-shim=none \
|
||||||
|
--buildtype debugoptimized
|
||||||
fi
|
fi
|
||||||
|
|
||||||
if [[ ! -d buildroot/build64 ]]; then
|
if [[ ! -d buildroot/build64 ]]; then
|
||||||
meson buildroot/build64 -Dwith-libressl-mode=shim --prefix=/usr --sysconfdir=/etc --datadir=/usr/share --libdir=/usr/lib64 -Dwith-shim=replacement -Dwith-steam-binary=/usr/lib64/steam/steam -Dwith-frontend=true -Dwith-new-libcxx-abi=true --buildtype debugoptimized
|
meson buildroot/build64 $DEFAULT_ARGS \
|
||||||
|
--prefix=/usr \
|
||||||
|
--sysconfdir=/etc \
|
||||||
|
--datadir=/usr/share \
|
||||||
|
--libdir=/usr/lib64 \
|
||||||
|
-Dwith-shim=replacement \
|
||||||
|
-Dwith-steam-binary=/usr/lib64/steam/steam \
|
||||||
|
-Dwith-frontend=true \
|
||||||
|
--buildtype debugoptimized
|
||||||
fi
|
fi
|
||||||
|
|
||||||
ninja -C buildroot/build32
|
ninja -C buildroot/build32
|
||||||
|
|||||||
+1
-1
@@ -5,7 +5,7 @@ git submodule init
|
|||||||
git submodule update
|
git submodule update
|
||||||
|
|
||||||
# Script for ikey because he went with meson. *shrug*
|
# Script for ikey because he went with meson. *shrug*
|
||||||
VERSION="0.7"
|
VERSION="0.7.3"
|
||||||
NAME="linux-steam-integration"
|
NAME="linux-steam-integration"
|
||||||
git-archive-all.sh --format tar --prefix ${NAME}-${VERSION}/ --verbose -t HEAD ${NAME}-${VERSION}.tar
|
git-archive-all.sh --format tar --prefix ${NAME}-${VERSION}/ --verbose -t HEAD ${NAME}-${VERSION}.tar
|
||||||
xz -9 "${NAME}-${VERSION}.tar"
|
xz -9 "${NAME}-${VERSION}.tar"
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: linux-steam-integration\n"
|
"Project-Id-Version: linux-steam-integration\n"
|
||||||
"Report-Msgid-Bugs-To: \n"
|
"Report-Msgid-Bugs-To: \n"
|
||||||
"POT-Creation-Date: 2017-11-05 19:28+0000\n"
|
"POT-Creation-Date: 2017-12-19 12:48+0000\n"
|
||||||
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
|
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
|
||||||
"Last-Translator: Davidmp <medipas@gmail.com>, 2017\n"
|
"Last-Translator: Davidmp <medipas@gmail.com>, 2017\n"
|
||||||
"Language-Team: Catalan (https://www.transifex.com/solus-project/teams/68407/ca/)\n"
|
"Language-Team: Catalan (https://www.transifex.com/solus-project/teams/68407/ca/)\n"
|
||||||
@@ -20,11 +20,11 @@ msgstr ""
|
|||||||
|
|
||||||
#. Sort out window bits
|
#. Sort out window bits
|
||||||
#. header label
|
#. header label
|
||||||
#: src/frontend/main-window.c:131 src/frontend/main-window.c:148
|
#: src/frontend/main-window.c:132 src/frontend/main-window.c:149
|
||||||
msgid "Linux Steam® Integration"
|
msgid "Linux Steam® Integration"
|
||||||
msgstr "Integració de Linux Steam®"
|
msgstr "Integració de Linux Steam®"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:162
|
#: src/frontend/main-window.c:163
|
||||||
msgid ""
|
msgid ""
|
||||||
"Control the behaviour of the Steam client and games. Settings will not take "
|
"Control the behaviour of the Steam client and games. Settings will not take "
|
||||||
"effect until the Steam Client is restarted. Use the 'Exit Steam' option to "
|
"effect until the Steam Client is restarted. Use the 'Exit Steam' option to "
|
||||||
@@ -34,20 +34,20 @@ msgstr ""
|
|||||||
" tindrà efecte fins que no es reiniciï el client d'Steam. Useu l'opció "
|
" tindrà efecte fins que no es reiniciï el client d'Steam. Useu l'opció "
|
||||||
"\"Surt de l'Steam\" per assegurar-vos que es tanqui."
|
"\"Surt de l'Steam\" per assegurar-vos que es tanqui."
|
||||||
|
|
||||||
#: src/frontend/main-window.c:191
|
#: src/frontend/main-window.c:192
|
||||||
msgid "Use native runtime"
|
msgid "Use native runtime"
|
||||||
msgstr "Usa l'entorn d'execució natiu"
|
msgstr "Usa l'entorn d'execució natiu"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:192
|
#: src/frontend/main-window.c:193
|
||||||
msgid "Switch between the native runtime and the bundled Steam runtime."
|
msgid "Switch between the native runtime and the bundled Steam runtime."
|
||||||
msgstr "Canvieu entre l'entorn natiu i l'entorn d'Steam agrupat."
|
msgstr "Canvieu entre l'entorn natiu i l'entorn d'Steam agrupat."
|
||||||
|
|
||||||
#. Label is shown to indicate we can't enable 32-bit option
|
#. Label is shown to indicate we can't enable 32-bit option
|
||||||
#: src/frontend/main-window.c:201
|
#: src/frontend/main-window.c:202
|
||||||
msgid "This option has been disabled as the system is already 32-bit"
|
msgid "This option has been disabled as the system is already 32-bit"
|
||||||
msgstr "Aquesta opció s'ha inhabilitat ja que el sistema ja és de 32 bits."
|
msgstr "Aquesta opció s'ha inhabilitat ja que el sistema ja és de 32 bits."
|
||||||
|
|
||||||
#: src/frontend/main-window.c:205
|
#: src/frontend/main-window.c:206
|
||||||
msgid ""
|
msgid ""
|
||||||
"This may workaround some broken games, but will disable the Steam store "
|
"This may workaround some broken games, but will disable the Steam store "
|
||||||
"browser."
|
"browser."
|
||||||
@@ -55,15 +55,15 @@ msgstr ""
|
|||||||
"Això pot solucionar alguns jocs trencats, però inhabilitarà el navegador de "
|
"Això pot solucionar alguns jocs trencats, però inhabilitarà el navegador de "
|
||||||
"la botiga d'Steam."
|
"la botiga d'Steam."
|
||||||
|
|
||||||
#: src/frontend/main-window.c:210
|
#: src/frontend/main-window.c:211
|
||||||
msgid "Force 32-bit mode for Steam"
|
msgid "Force 32-bit mode for Steam"
|
||||||
msgstr "Força el mode de 32 bits per a l'Steam"
|
msgstr "Força el mode de 32 bits per a l'Steam"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:218
|
#: src/frontend/main-window.c:219
|
||||||
msgid "Use the intercept library"
|
msgid "Use the intercept library"
|
||||||
msgstr "Usa la biblioteca d'intercepció"
|
msgstr "Usa la biblioteca d'intercepció"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:219
|
#: src/frontend/main-window.c:220
|
||||||
msgid ""
|
msgid ""
|
||||||
"Force Steam applications to use more native libraries to maximise "
|
"Force Steam applications to use more native libraries to maximise "
|
||||||
"compatibility."
|
"compatibility."
|
||||||
@@ -71,16 +71,28 @@ msgstr ""
|
|||||||
"Força que les aplicacions de l'Steam usin més biblioteques natives per "
|
"Força que les aplicacions de l'Steam usin més biblioteques natives per "
|
||||||
"maximitzar la compatibilitat."
|
"maximitzar la compatibilitat."
|
||||||
|
|
||||||
#: src/frontend/main-window.c:228
|
#: src/frontend/main-window.c:229
|
||||||
msgid "Use the redirect library"
|
msgid "Use the redirect library"
|
||||||
msgstr "Usa la biblioteca de redirecció"
|
msgstr "Usa la biblioteca de redirecció"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:229
|
#: src/frontend/main-window.c:230
|
||||||
msgid "Override system calls to fix known bugs in some Linux ports."
|
msgid "Override system calls to fix known bugs in some Linux ports."
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Anul·la les crides de sistema per corregir errors coneguts en algunes "
|
"Anul·la les crides de sistema per corregir errors coneguts en algunes "
|
||||||
"versions de Linux."
|
"versions de Linux."
|
||||||
|
|
||||||
#: src/frontend/main-window.c:383
|
#: src/frontend/main-window.c:237
|
||||||
|
msgid "Use the Unity fullscreen workaround"
|
||||||
|
msgstr "Usa la solució provisional de pantalla completa de l'Unity."
|
||||||
|
|
||||||
|
#: src/frontend/main-window.c:238
|
||||||
|
msgid ""
|
||||||
|
"Prevent some Unity games from launching in full screen mode to fix numerous "
|
||||||
|
"issues"
|
||||||
|
msgstr ""
|
||||||
|
"Evita que alguns jocs d'Unity s'obrin en pantalla completa per tal de "
|
||||||
|
"corregir uns quants problemes."
|
||||||
|
|
||||||
|
#: src/frontend/main-window.c:403
|
||||||
msgid "Failed to save configuration"
|
msgid "Failed to save configuration"
|
||||||
msgstr "Ha fallat desar la configuració"
|
msgstr "Ha fallat desar la configuració"
|
||||||
|
|||||||
+26
-14
@@ -8,9 +8,9 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: linux-steam-integration\n"
|
"Project-Id-Version: linux-steam-integration\n"
|
||||||
"Report-Msgid-Bugs-To: \n"
|
"Report-Msgid-Bugs-To: \n"
|
||||||
"POT-Creation-Date: 2017-11-05 19:28+0000\n"
|
"POT-Creation-Date: 2017-12-19 12:48+0000\n"
|
||||||
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
|
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
|
||||||
"Last-Translator: Fabio Forni <fabio94xx@gmail.com>, 2017\n"
|
"Last-Translator: Fabio <fabio0x@keemail.me>, 2017\n"
|
||||||
"Language-Team: Italian (Italy) (https://www.transifex.com/solus-project/teams/68407/it_IT/)\n"
|
"Language-Team: Italian (Italy) (https://www.transifex.com/solus-project/teams/68407/it_IT/)\n"
|
||||||
"MIME-Version: 1.0\n"
|
"MIME-Version: 1.0\n"
|
||||||
"Content-Type: text/plain; charset=UTF-8\n"
|
"Content-Type: text/plain; charset=UTF-8\n"
|
||||||
@@ -20,11 +20,11 @@ msgstr ""
|
|||||||
|
|
||||||
#. Sort out window bits
|
#. Sort out window bits
|
||||||
#. header label
|
#. header label
|
||||||
#: src/frontend/main-window.c:131 src/frontend/main-window.c:148
|
#: src/frontend/main-window.c:132 src/frontend/main-window.c:149
|
||||||
msgid "Linux Steam® Integration"
|
msgid "Linux Steam® Integration"
|
||||||
msgstr "Linux Steam® Integration"
|
msgstr "Linux Steam® Integration"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:162
|
#: src/frontend/main-window.c:163
|
||||||
msgid ""
|
msgid ""
|
||||||
"Control the behaviour of the Steam client and games. Settings will not take "
|
"Control the behaviour of the Steam client and games. Settings will not take "
|
||||||
"effect until the Steam Client is restarted. Use the 'Exit Steam' option to "
|
"effect until the Steam Client is restarted. Use the 'Exit Steam' option to "
|
||||||
@@ -34,20 +34,20 @@ msgstr ""
|
|||||||
"non avranno effetto finché il client Steam non sarà riavviato. Usa l'opzione"
|
"non avranno effetto finché il client Steam non sarà riavviato. Usa l'opzione"
|
||||||
" \"Esci da Steam\" per assicurarti che venga davvero chiuso."
|
" \"Esci da Steam\" per assicurarti che venga davvero chiuso."
|
||||||
|
|
||||||
#: src/frontend/main-window.c:191
|
#: src/frontend/main-window.c:192
|
||||||
msgid "Use native runtime"
|
msgid "Use native runtime"
|
||||||
msgstr "Use ambiente di runtime nativo"
|
msgstr "Use ambiente di runtime nativo"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:192
|
#: src/frontend/main-window.c:193
|
||||||
msgid "Switch between the native runtime and the bundled Steam runtime."
|
msgid "Switch between the native runtime and the bundled Steam runtime."
|
||||||
msgstr "Scegli tra l'ambiente di runtime nativo e quello integrato in Steam."
|
msgstr "Scegli tra l'ambiente di runtime nativo e quello integrato in Steam."
|
||||||
|
|
||||||
#. Label is shown to indicate we can't enable 32-bit option
|
#. Label is shown to indicate we can't enable 32-bit option
|
||||||
#: src/frontend/main-window.c:201
|
#: src/frontend/main-window.c:202
|
||||||
msgid "This option has been disabled as the system is already 32-bit"
|
msgid "This option has been disabled as the system is already 32-bit"
|
||||||
msgstr "Questa opzione è disabilitata perché il sistema è già a 32-bit"
|
msgstr "Questa opzione è disabilitata perché il sistema è già a 32-bit"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:205
|
#: src/frontend/main-window.c:206
|
||||||
msgid ""
|
msgid ""
|
||||||
"This may workaround some broken games, but will disable the Steam store "
|
"This may workaround some broken games, but will disable the Steam store "
|
||||||
"browser."
|
"browser."
|
||||||
@@ -55,15 +55,15 @@ msgstr ""
|
|||||||
"Può correggere alcuni giochi non funzionanti, ma disabiliterà la navigazione"
|
"Può correggere alcuni giochi non funzionanti, ma disabiliterà la navigazione"
|
||||||
" nel negozio Steam."
|
" nel negozio Steam."
|
||||||
|
|
||||||
#: src/frontend/main-window.c:210
|
#: src/frontend/main-window.c:211
|
||||||
msgid "Force 32-bit mode for Steam"
|
msgid "Force 32-bit mode for Steam"
|
||||||
msgstr "Forza Steam a 32-bit"
|
msgstr "Forza Steam a 32-bit"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:218
|
#: src/frontend/main-window.c:219
|
||||||
msgid "Use the intercept library"
|
msgid "Use the intercept library"
|
||||||
msgstr "Usa la libreria di intercettazione"
|
msgstr "Usa la libreria di intercettazione"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:219
|
#: src/frontend/main-window.c:220
|
||||||
msgid ""
|
msgid ""
|
||||||
"Force Steam applications to use more native libraries to maximise "
|
"Force Steam applications to use more native libraries to maximise "
|
||||||
"compatibility."
|
"compatibility."
|
||||||
@@ -71,16 +71,28 @@ msgstr ""
|
|||||||
"Forza le applicazioni di Steam a usare ancor più librerie native per "
|
"Forza le applicazioni di Steam a usare ancor più librerie native per "
|
||||||
"massimizzare la compatibilità."
|
"massimizzare la compatibilità."
|
||||||
|
|
||||||
#: src/frontend/main-window.c:228
|
#: src/frontend/main-window.c:229
|
||||||
msgid "Use the redirect library"
|
msgid "Use the redirect library"
|
||||||
msgstr "Usa la libreria di redirezione"
|
msgstr "Usa la libreria di redirezione"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:229
|
#: src/frontend/main-window.c:230
|
||||||
msgid "Override system calls to fix known bugs in some Linux ports."
|
msgid "Override system calls to fix known bugs in some Linux ports."
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Sostituisce le chiamate di sistema per correggere i bug noti di alcuni "
|
"Sostituisce le chiamate di sistema per correggere i bug noti di alcuni "
|
||||||
"porting su Linux."
|
"porting su Linux."
|
||||||
|
|
||||||
#: src/frontend/main-window.c:383
|
#: src/frontend/main-window.c:237
|
||||||
|
msgid "Use the Unity fullscreen workaround"
|
||||||
|
msgstr "Aggira il problema di Unity a schermo intero"
|
||||||
|
|
||||||
|
#: src/frontend/main-window.c:238
|
||||||
|
msgid ""
|
||||||
|
"Prevent some Unity games from launching in full screen mode to fix numerous "
|
||||||
|
"issues"
|
||||||
|
msgstr ""
|
||||||
|
"Evita che alcuni giochi basati su Unity partano a schermo intero per "
|
||||||
|
"correggere svariate problematiche"
|
||||||
|
|
||||||
|
#: src/frontend/main-window.c:403
|
||||||
msgid "Failed to save configuration"
|
msgid "Failed to save configuration"
|
||||||
msgstr "Errore durante il salvataggio della configurazione"
|
msgstr "Errore durante il salvataggio della configurazione"
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: linux-steam-integration\n"
|
"Project-Id-Version: linux-steam-integration\n"
|
||||||
"Report-Msgid-Bugs-To: \n"
|
"Report-Msgid-Bugs-To: \n"
|
||||||
"POT-Creation-Date: 2017-11-05 19:28+0000\n"
|
"POT-Creation-Date: 2017-12-19 12:48+0000\n"
|
||||||
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
|
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
|
||||||
"Last-Translator: Moo <moose@mail.ru>, 2017\n"
|
"Last-Translator: Moo <moose@mail.ru>, 2017\n"
|
||||||
"Language-Team: Lithuanian (https://www.transifex.com/solus-project/teams/68407/lt/)\n"
|
"Language-Team: Lithuanian (https://www.transifex.com/solus-project/teams/68407/lt/)\n"
|
||||||
@@ -20,11 +20,11 @@ msgstr ""
|
|||||||
|
|
||||||
#. Sort out window bits
|
#. Sort out window bits
|
||||||
#. header label
|
#. header label
|
||||||
#: src/frontend/main-window.c:131 src/frontend/main-window.c:148
|
#: src/frontend/main-window.c:132 src/frontend/main-window.c:149
|
||||||
msgid "Linux Steam® Integration"
|
msgid "Linux Steam® Integration"
|
||||||
msgstr "Linux Steam® integracija"
|
msgstr "Linux Steam® integracija"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:162
|
#: src/frontend/main-window.c:163
|
||||||
msgid ""
|
msgid ""
|
||||||
"Control the behaviour of the Steam client and games. Settings will not take "
|
"Control the behaviour of the Steam client and games. Settings will not take "
|
||||||
"effect until the Steam Client is restarted. Use the 'Exit Steam' option to "
|
"effect until the Steam Client is restarted. Use the 'Exit Steam' option to "
|
||||||
@@ -34,21 +34,21 @@ msgstr ""
|
|||||||
"Steam klientas nebus paleistas iš naujo. Norėdami užtikrinti, kad programa "
|
"Steam klientas nebus paleistas iš naujo. Norėdami užtikrinti, kad programa "
|
||||||
"Steam baigtų darbą, naudokite parametrą \"Išeiti iš Steam\"."
|
"Steam baigtų darbą, naudokite parametrą \"Išeiti iš Steam\"."
|
||||||
|
|
||||||
#: src/frontend/main-window.c:191
|
#: src/frontend/main-window.c:192
|
||||||
msgid "Use native runtime"
|
msgid "Use native runtime"
|
||||||
msgstr "Naudoti savą vykdymo aplinką"
|
msgstr "Naudoti savą vykdymo aplinką"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:192
|
#: src/frontend/main-window.c:193
|
||||||
msgid "Switch between the native runtime and the bundled Steam runtime."
|
msgid "Switch between the native runtime and the bundled Steam runtime."
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Perjungti tarp savos vykdymo aplinkos ir pridėtinės Steam vykdymo aplinkos."
|
"Perjungti tarp savos vykdymo aplinkos ir pridėtinės Steam vykdymo aplinkos."
|
||||||
|
|
||||||
#. Label is shown to indicate we can't enable 32-bit option
|
#. Label is shown to indicate we can't enable 32-bit option
|
||||||
#: src/frontend/main-window.c:201
|
#: src/frontend/main-window.c:202
|
||||||
msgid "This option has been disabled as the system is already 32-bit"
|
msgid "This option has been disabled as the system is already 32-bit"
|
||||||
msgstr "Šis parametras buvo išjungtas, nes sistema jau ir yra 32-bitų"
|
msgstr "Šis parametras buvo išjungtas, nes sistema jau ir yra 32-bitų"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:205
|
#: src/frontend/main-window.c:206
|
||||||
msgid ""
|
msgid ""
|
||||||
"This may workaround some broken games, but will disable the Steam store "
|
"This may workaround some broken games, but will disable the Steam store "
|
||||||
"browser."
|
"browser."
|
||||||
@@ -56,15 +56,15 @@ msgstr ""
|
|||||||
"Tai galėti padėti apeiti kai kurių neveikiančių žaidimų problemas, tačiau "
|
"Tai galėti padėti apeiti kai kurių neveikiančių žaidimų problemas, tačiau "
|
||||||
"išjungs Steam parduotuvės naršyklę."
|
"išjungs Steam parduotuvės naršyklę."
|
||||||
|
|
||||||
#: src/frontend/main-window.c:210
|
#: src/frontend/main-window.c:211
|
||||||
msgid "Force 32-bit mode for Steam"
|
msgid "Force 32-bit mode for Steam"
|
||||||
msgstr "Programai Steam priverstinai naudoti 32-bitų veikseną"
|
msgstr "Programai Steam priverstinai naudoti 32-bitų veikseną"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:218
|
#: src/frontend/main-window.c:219
|
||||||
msgid "Use the intercept library"
|
msgid "Use the intercept library"
|
||||||
msgstr "Naudoti perėmimo biblioteką"
|
msgstr "Naudoti perėmimo biblioteką"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:219
|
#: src/frontend/main-window.c:220
|
||||||
msgid ""
|
msgid ""
|
||||||
"Force Steam applications to use more native libraries to maximise "
|
"Force Steam applications to use more native libraries to maximise "
|
||||||
"compatibility."
|
"compatibility."
|
||||||
@@ -72,16 +72,28 @@ msgstr ""
|
|||||||
"Priversti Steam programas naudoti labiau savas bibliotekas, siekiant "
|
"Priversti Steam programas naudoti labiau savas bibliotekas, siekiant "
|
||||||
"padidinti suderinamumą."
|
"padidinti suderinamumą."
|
||||||
|
|
||||||
#: src/frontend/main-window.c:228
|
#: src/frontend/main-window.c:229
|
||||||
msgid "Use the redirect library"
|
msgid "Use the redirect library"
|
||||||
msgstr "Naudoti peradresavimo biblioteką"
|
msgstr "Naudoti peradresavimo biblioteką"
|
||||||
|
|
||||||
#: src/frontend/main-window.c:229
|
#: src/frontend/main-window.c:230
|
||||||
msgid "Override system calls to fix known bugs in some Linux ports."
|
msgid "Override system calls to fix known bugs in some Linux ports."
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Nustelbti sistemines iškvietas, siekiant pataisyti žinomas klaidas kai "
|
"Nustelbti sistemines iškvietas, siekiant pataisyti žinomas klaidas kai "
|
||||||
"kuriuose Linux perkėlimuose."
|
"kuriuose Linux perkėlimuose."
|
||||||
|
|
||||||
#: src/frontend/main-window.c:383
|
#: src/frontend/main-window.c:237
|
||||||
|
msgid "Use the Unity fullscreen workaround"
|
||||||
|
msgstr "Naudoti Unity viso ekrano problemos apėjimą"
|
||||||
|
|
||||||
|
#: src/frontend/main-window.c:238
|
||||||
|
msgid ""
|
||||||
|
"Prevent some Unity games from launching in full screen mode to fix numerous "
|
||||||
|
"issues"
|
||||||
|
msgstr ""
|
||||||
|
"Neleisti kai kuriems Unity žaidimams pasileisti viso ekrano veiksenoje, "
|
||||||
|
"siekiant pataisyti daugelį klaidų"
|
||||||
|
|
||||||
|
#: src/frontend/main-window.c:403
|
||||||
msgid "Failed to save configuration"
|
msgid "Failed to save configuration"
|
||||||
msgstr "Nepavyko įrašyti konfigūracijos"
|
msgstr "Nepavyko įrašyti konfigūracijos"
|
||||||
|
|||||||
@@ -0,0 +1,4 @@
|
|||||||
|
install_data(
|
||||||
|
'pulseaudio',
|
||||||
|
install_dir: join_paths(path_fake_scripts_dir, 'pulseaudio'),
|
||||||
|
)
|
||||||
Executable
+12
@@ -0,0 +1,12 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# Work around games using libfmod which is determined to execute:
|
||||||
|
# pulseaudio --check > /dev/null 2>&1
|
||||||
|
|
||||||
|
if [[ ! -z "$1" ]]; then
|
||||||
|
if [[ "$1" == "--check" ]] ; then
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
|
||||||
|
exec /usr/bin/pulseaudio $*
|
||||||
+2
-1
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2016-2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
|
|||||||
+2
-1
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2016-2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
|
|||||||
+2
-1
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2016-2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
|
|||||||
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2016-2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
@@ -114,7 +115,7 @@ static void lsi_settings_window_init(LsiSettingsWindow *self)
|
|||||||
lsi_config_load_defaults(&self->config);
|
lsi_config_load_defaults(&self->config);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Conditionally apply CSD */
|
/* Conditionally apply CSD */
|
||||||
#if GTK_CHECK_VERSION(3, 12, 0)
|
#if GTK_CHECK_VERSION(3, 12, 0)
|
||||||
xdg_desktop = g_getenv("XDG_CURRENT_DESKTOP");
|
xdg_desktop = g_getenv("XDG_CURRENT_DESKTOP");
|
||||||
if (xdg_desktop && (strstr(xdg_desktop, "GNOME:") || strstr(xdg_desktop, ":GNOME") ||
|
if (xdg_desktop && (strstr(xdg_desktop, "GNOME:") || strstr(xdg_desktop, ":GNOME") ||
|
||||||
|
|||||||
+2
-1
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2016-2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
|
|||||||
@@ -20,5 +20,6 @@ if with_frontend == true
|
|||||||
link_lsi,
|
link_lsi,
|
||||||
],
|
],
|
||||||
install: true,
|
install: true,
|
||||||
|
install_dir: path_bindir,
|
||||||
)
|
)
|
||||||
endif
|
endif
|
||||||
|
|||||||
+18
-2
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2016-2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
@@ -86,6 +87,7 @@ static const char *steam_allowed[] = {
|
|||||||
"panorama",
|
"panorama",
|
||||||
"libpangoft2-1.0.so",
|
"libpangoft2-1.0.so",
|
||||||
"libpango-1.0.so",
|
"libpango-1.0.so",
|
||||||
|
"libpangocairo-1.0.so",
|
||||||
|
|
||||||
/* steamwebhelper */
|
/* steamwebhelper */
|
||||||
"libcef.so",
|
"libcef.so",
|
||||||
@@ -118,7 +120,14 @@ static const char *vendor_blacklist[] = {
|
|||||||
|
|
||||||
/* Ensure we don't match weird made up cruft like "libSDL2_locale" */
|
/* Ensure we don't match weird made up cruft like "libSDL2_locale" */
|
||||||
"libSDL-1.2",
|
"libSDL-1.2",
|
||||||
|
|
||||||
|
#if UINTPTR_MAX == 0xffffffffffffffff
|
||||||
|
/* Only blacklist SDL on native 64-bit builds
|
||||||
|
* 32-bit builds tend to do weird stuff, like ship incompatible
|
||||||
|
* patched builds of libSDL (Don't Starve, for example)
|
||||||
|
*/
|
||||||
"libSDL2-2",
|
"libSDL2-2",
|
||||||
|
#endif
|
||||||
"libSDL2_ttf",
|
"libSDL2_ttf",
|
||||||
"libSDL_ttf",
|
"libSDL_ttf",
|
||||||
"libSDL2_image",
|
"libSDL2_image",
|
||||||
@@ -262,6 +271,8 @@ static const char *vendor_transmute_source[] = {
|
|||||||
#ifdef LSI_OVERRIDE_LIBRESSL
|
#ifdef LSI_OVERRIDE_LIBRESSL
|
||||||
"libcrypto.so.36",
|
"libcrypto.so.36",
|
||||||
"libssl.so.37",
|
"libssl.so.37",
|
||||||
|
"libcrypto.so.42",
|
||||||
|
"libssl.so.44",
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* old name for openal */
|
/* old name for openal */
|
||||||
@@ -297,9 +308,13 @@ static const char *vendor_transmute_target[] = {
|
|||||||
#if defined(LSI_LIBRESSL_MODE_SHIM)
|
#if defined(LSI_LIBRESSL_MODE_SHIM)
|
||||||
"libcrypto" LSI_LIBRESSL_SUFFIX ".so",
|
"libcrypto" LSI_LIBRESSL_SUFFIX ".so",
|
||||||
"libssl" LSI_LIBRESSL_SUFFIX ".so",
|
"libssl" LSI_LIBRESSL_SUFFIX ".so",
|
||||||
|
"libcrypto" LSI_LIBRESSL_SUFFIX ".so",
|
||||||
|
"libssl" LSI_LIBRESSL_SUFFIX ".so",
|
||||||
#elif defined(LSI_LIBRESSL_MODE_NATIVE)
|
#elif defined(LSI_LIBRESSL_MODE_NATIVE)
|
||||||
"libcrypto.so.1.0.0",
|
"libcrypto.so.1.0.0",
|
||||||
"libssl.so.1.0.0",
|
"libssl.so.1.0.0",
|
||||||
|
"libcrypto.so.1.0.0",
|
||||||
|
"libssl.so.1.0.0",
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* new name for openal */
|
/* new name for openal */
|
||||||
@@ -392,14 +407,15 @@ static bool lsi_override_x86_derp(const char *orig_name, const char **soname)
|
|||||||
orig_name,
|
orig_name,
|
||||||
path_lookup);
|
path_lookup);
|
||||||
return true;
|
return true;
|
||||||
|
}
|
||||||
#else
|
#else
|
||||||
static bool lsi_override_x86_derp(__lsi_unused__ const char *orig_name,
|
static bool lsi_override_x86_derp(__lsi_unused__ const char *orig_name,
|
||||||
__lsi_unused__ const char **soname)
|
__lsi_unused__ const char **soname)
|
||||||
{
|
{
|
||||||
/* Don't perform x86 translation on 32-bit machines */
|
/* Don't perform x86 translation on 32-bit machines */
|
||||||
return false;
|
return false;
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Internal helper for path replacement to host lib
|
* Internal helper for path replacement to host lib
|
||||||
|
|||||||
+1
-1
Submodule src/libnica updated: e71a442667...8ec3cf2291
+2
-1
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2016-2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
|
|||||||
+49
-322
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
@@ -12,23 +13,26 @@
|
|||||||
#define _GNU_SOURCE
|
#define _GNU_SOURCE
|
||||||
|
|
||||||
#include <dlfcn.h>
|
#include <dlfcn.h>
|
||||||
#include <errno.h>
|
|
||||||
#include <fcntl.h>
|
|
||||||
#include <libgen.h>
|
#include <libgen.h>
|
||||||
#include <stdarg.h>
|
#include <stdarg.h>
|
||||||
#include <stdbool.h>
|
#include <stdbool.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <sys/mman.h>
|
|
||||||
#include <sys/stat.h>
|
#include "config.h"
|
||||||
#include <unistd.h>
|
|
||||||
|
/* Expose getpwuid override in snapd */
|
||||||
|
#ifdef HAVE_SNAPD_SUPPORT
|
||||||
|
#include <pwd.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
#include "../common/common.h"
|
#include "../common/common.h"
|
||||||
#include "../common/files.h"
|
#include "../common/files.h"
|
||||||
#include "../common/log.h"
|
#include "../common/log.h"
|
||||||
#include "nica/util.h"
|
#include "nica/util.h"
|
||||||
|
|
||||||
|
#include "private.h"
|
||||||
#include "profile.h"
|
#include "profile.h"
|
||||||
#include "redirect.h"
|
#include "redirect.h"
|
||||||
|
|
||||||
@@ -40,33 +44,6 @@
|
|||||||
.func = (void **)(&lsi_table.x), .func_size = sizeof(lsi_table.x) \
|
.func = (void **)(&lsi_table.x), .func_size = sizeof(lsi_table.x) \
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Cheap and cheerful, this is our default fake unity3d config which we write
|
|
||||||
* out to trick unity3d games into reading a non broken config on Linux.
|
|
||||||
* This forces the equivalent of "-screen-fullscreen 0" because the older
|
|
||||||
* Unity builds will set fullscreen to 1, but they'll also set the resolution
|
|
||||||
* width and height to 0 (which is then clamped)
|
|
||||||
*/
|
|
||||||
static const char *unity3d_config =
|
|
||||||
"\
|
|
||||||
<unity_prefs version_major=\"1\" version_minor=\"1\">\n\
|
|
||||||
<pref name=\"Screenmanager Is Fullscreen mode\" type=\"int\">0</pref>\n\
|
|
||||||
</unity_prefs>\n\
|
|
||||||
";
|
|
||||||
|
|
||||||
/**
|
|
||||||
* When we rewrite the config file in place we'll repllace the "Is Fullscreen mode"
|
|
||||||
* line with this one so that we forcibly disable it.
|
|
||||||
*/
|
|
||||||
static const char *unity3d_snippet =
|
|
||||||
" <pref name=\"Screenmanager Is Fullscreen mode\" type=\"int\">0</pref>\n";
|
|
||||||
|
|
||||||
static void lsi_maybe_init_unity3d(const char *p);
|
|
||||||
static void lsi_unity_backup_config(void);
|
|
||||||
static FILE *lsi_unity_redirect(const char *p, const char *modes);
|
|
||||||
static FILE *lsi_unity_get_config_file(const char *modes);
|
|
||||||
static void lsi_unity_trim_copy_config(FILE *from, FILE *to);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Whether we've initialised yet or not.
|
* Whether we've initialised yet or not.
|
||||||
*/
|
*/
|
||||||
@@ -78,13 +55,6 @@ static volatile bool lsi_init = false;
|
|||||||
*/
|
*/
|
||||||
static volatile bool lsi_override = false;
|
static volatile bool lsi_override = false;
|
||||||
|
|
||||||
/**
|
|
||||||
* Handle definitions
|
|
||||||
*/
|
|
||||||
typedef int (*lsi_open_file)(const char *p, int flags, mode_t mode);
|
|
||||||
|
|
||||||
typedef FILE *(*lsi_fopen64_file)(const char *p, const char *modes);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Known profiles
|
* Known profiles
|
||||||
*/
|
*/
|
||||||
@@ -93,29 +63,6 @@ static lsi_profile_generator_func generators[] = {
|
|||||||
&lsi_redirect_profile_new_project_highrise,
|
&lsi_redirect_profile_new_project_highrise,
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
|
||||||
* Global storage of handles for nicer organisation.
|
|
||||||
*/
|
|
||||||
typedef struct LsiRedirectTable {
|
|
||||||
lsi_open_file open;
|
|
||||||
lsi_fopen64_file fopen64;
|
|
||||||
|
|
||||||
/* Allow future handle opens.. */
|
|
||||||
struct {
|
|
||||||
void *libc;
|
|
||||||
} handles;
|
|
||||||
|
|
||||||
/* Our shm_open() unity3d redirect.. */
|
|
||||||
struct {
|
|
||||||
char *original_config_path;
|
|
||||||
char *config_path;
|
|
||||||
char *shm_path;
|
|
||||||
bool enabled;
|
|
||||||
bool failed;
|
|
||||||
bool had_init;
|
|
||||||
} unity3d;
|
|
||||||
} LsiRedirectTable;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Easy mapping to make it quick and easy to add new function overrides
|
* Easy mapping to make it quick and easy to add new function overrides
|
||||||
*/
|
*/
|
||||||
@@ -143,6 +90,9 @@ static LsiRedirectProfile *lsi_profile = NULL;
|
|||||||
static LsiSymbolBinding lsi_libc_bindings[] = {
|
static LsiSymbolBinding lsi_libc_bindings[] = {
|
||||||
SYMBOL_BINDING(libc, open),
|
SYMBOL_BINDING(libc, open),
|
||||||
SYMBOL_BINDING(libc, fopen64),
|
SYMBOL_BINDING(libc, fopen64),
|
||||||
|
#ifdef HAVE_SNAPD_SUPPORT
|
||||||
|
SYMBOL_BINDING(libc, getpwuid),
|
||||||
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -160,21 +110,7 @@ __attribute__((destructor)) static void lsi_redirect_shutdown(void)
|
|||||||
}
|
}
|
||||||
lsi_init = false;
|
lsi_init = false;
|
||||||
|
|
||||||
if (lsi_table.unity3d.original_config_path) {
|
lsi_unity_cleanup(&lsi_table);
|
||||||
lsi_unity_backup_config();
|
|
||||||
free(lsi_table.unity3d.original_config_path);
|
|
||||||
lsi_table.unity3d.original_config_path = NULL;
|
|
||||||
}
|
|
||||||
if (lsi_table.unity3d.config_path) {
|
|
||||||
free(lsi_table.unity3d.config_path);
|
|
||||||
lsi_table.unity3d.config_path = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (lsi_table.unity3d.shm_path) {
|
|
||||||
(void)shm_unlink(lsi_table.unity3d.shm_path);
|
|
||||||
free(lsi_table.unity3d.shm_path);
|
|
||||||
lsi_table.unity3d.shm_path = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (lsi_table.handles.libc) {
|
if (lsi_table.handles.libc) {
|
||||||
dlclose(lsi_table.handles.libc);
|
dlclose(lsi_table.handles.libc);
|
||||||
@@ -261,7 +197,6 @@ __attribute__((constructor)) static void lsi_redirect_init(void)
|
|||||||
autofree(char) *process_name = NULL;
|
autofree(char) *process_name = NULL;
|
||||||
char **paths = NULL;
|
char **paths = NULL;
|
||||||
char **orig = NULL;
|
char **orig = NULL;
|
||||||
autofree(char) *xdg_config_dir = NULL;
|
|
||||||
|
|
||||||
/* Absolute path to the process for fine-grained matching */
|
/* Absolute path to the process for fine-grained matching */
|
||||||
process_name = lsi_get_process_name();
|
process_name = lsi_get_process_name();
|
||||||
@@ -271,25 +206,7 @@ __attribute__((constructor)) static void lsi_redirect_init(void)
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Ensure we know the path to unity3d config */
|
lsi_unity_startup(&lsi_table);
|
||||||
xdg_config_dir = lsi_get_user_config_dir();
|
|
||||||
if (asprintf(&lsi_table.unity3d.config_path, "%s/unity3d", xdg_config_dir) < 0) {
|
|
||||||
fputs("OOM\n", stderr);
|
|
||||||
abort();
|
|
||||||
}
|
|
||||||
|
|
||||||
/* shm path for our fake unity3d config path */
|
|
||||||
if (asprintf(&lsi_table.unity3d.shm_path,
|
|
||||||
"/u%d-LinuxSteamIntegration.unity3d.%d",
|
|
||||||
getuid(),
|
|
||||||
getpgrp()) < 0) {
|
|
||||||
fputs("OOM\n", stderr);
|
|
||||||
abort();
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Symbolic, we don't just use this for anyone, yknow. :P */
|
|
||||||
lsi_table.unity3d.enabled = false;
|
|
||||||
lsi_table.unity3d.failed = false;
|
|
||||||
|
|
||||||
/* Grab the steam installation directories */
|
/* Grab the steam installation directories */
|
||||||
orig = paths = lsi_get_steam_paths();
|
orig = paths = lsi_get_steam_paths();
|
||||||
@@ -366,162 +283,6 @@ static char *lsi_get_redirect_path(const char *syscall_id, LsiRedirectOperation
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* The unity3d config path has been accessed, so we need to turn on our
|
|
||||||
* workaround for unity3d prefs
|
|
||||||
*/
|
|
||||||
static void lsi_maybe_init_unity3d(const char *p)
|
|
||||||
{
|
|
||||||
if (lsi_table.unity3d.enabled) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (lsi_table.unity3d.config_path && !strstr(p, lsi_table.unity3d.config_path)) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Set by the main shim */
|
|
||||||
if (!getenv("LSI_USE_UNITY_HACK")) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* We're in action */
|
|
||||||
lsi_table.unity3d.enabled = true;
|
|
||||||
lsi_log_set_id("unity3d");
|
|
||||||
lsi_log_info("Activating \"black screen of nope\" workaround");
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline bool str_has_prefix(const char *a, const char *b)
|
|
||||||
{
|
|
||||||
size_t lena, lenb;
|
|
||||||
lena = strlen(a);
|
|
||||||
lenb = strlen(b);
|
|
||||||
if (lenb > lena) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
return strncmp(a, b, lenb) == 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Determine if the input path is a unity3d "prefs" file
|
|
||||||
*/
|
|
||||||
static bool is_unity3d_prefs_file(const char *p)
|
|
||||||
{
|
|
||||||
autofree(char) *clone = NULL;
|
|
||||||
char *basenom = NULL;
|
|
||||||
|
|
||||||
/* Must only happen when enabled */
|
|
||||||
if (!lsi_table.unity3d.enabled) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* We found it already */
|
|
||||||
if (lsi_table.unity3d.original_config_path) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Must be in config path */
|
|
||||||
if (!str_has_prefix(p, lsi_table.unity3d.config_path)) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
clone = strdup(p);
|
|
||||||
if (!clone) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
basenom = basename(clone);
|
|
||||||
if (!basenom) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Must be called "prefs" */
|
|
||||||
return strcmp(basenom, "prefs") == 0 ? true : false;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Copy the config from the @from file to the @to file, which
|
|
||||||
* will also strip out any "evil" lines, i.e. the fullscreen
|
|
||||||
* stanza.
|
|
||||||
*
|
|
||||||
* If the input file does not exist, the default configuration
|
|
||||||
* will be used.
|
|
||||||
*/
|
|
||||||
static void lsi_unity_trim_copy_config(FILE *from, FILE *to)
|
|
||||||
{
|
|
||||||
char *buf = NULL;
|
|
||||||
size_t sn = 0;
|
|
||||||
ssize_t r = 0;
|
|
||||||
|
|
||||||
/* No input? Write the default configuration then */
|
|
||||||
if (!from) {
|
|
||||||
if (fwrite(unity3d_config, strlen(unity3d_config), 1, to) != 1) {
|
|
||||||
lsi_log_error("Failed to create initial Unity3D config: %s",
|
|
||||||
strerror(errno));
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Have an input file, write to the output but omit all the bad lines */
|
|
||||||
while ((r = getline(&buf, &sn, from)) != -1) {
|
|
||||||
const char *to_write = NULL;
|
|
||||||
|
|
||||||
/* Rewrite this line, it breaks games. */
|
|
||||||
if (strstr(buf, "Screenmanager Is Fullscreen mode")) {
|
|
||||||
to_write = unity3d_snippet;
|
|
||||||
r = strlen(to_write);
|
|
||||||
} else {
|
|
||||||
to_write = buf;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (fwrite(to_write, r, 1, to) != 1) {
|
|
||||||
lsi_log_error("Failed to write Unity3D config: %s", strerror(errno));
|
|
||||||
goto failed;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (buf) {
|
|
||||||
free(buf);
|
|
||||||
buf = NULL;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fflush(to);
|
|
||||||
|
|
||||||
failed:
|
|
||||||
if (buf) {
|
|
||||||
free(buf);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Clone the existing shm configuration into the real config path, and copy
|
|
||||||
* all lines that we "like"
|
|
||||||
*
|
|
||||||
* Basically this ensures we force the dumped config to omit the fullscreen
|
|
||||||
* options as they break so many games.
|
|
||||||
*/
|
|
||||||
static void lsi_unity_backup_config()
|
|
||||||
{
|
|
||||||
autofree(FILE) *shm_file = NULL;
|
|
||||||
autofree(FILE) *dest_file = NULL;
|
|
||||||
|
|
||||||
if (!lsi_table.unity3d.enabled || !lsi_table.unity3d.original_config_path) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
shm_file = lsi_unity_get_config_file("r");
|
|
||||||
if (!shm_file) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
dest_file = lsi_table.fopen64(lsi_table.unity3d.original_config_path, "w");
|
|
||||||
if (!dest_file) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
lsi_log_debug("Saved Unity3D config to %s", lsi_table.unity3d.original_config_path);
|
|
||||||
lsi_unity_trim_copy_config(shm_file, dest_file);
|
|
||||||
}
|
|
||||||
|
|
||||||
_nica_public_ int open(const char *p, int flags, ...)
|
_nica_public_ int open(const char *p, int flags, ...)
|
||||||
{
|
{
|
||||||
va_list va;
|
va_list va;
|
||||||
@@ -539,7 +300,7 @@ _nica_public_ int open(const char *p, int flags, ...)
|
|||||||
mode = va_arg(va, mode_t);
|
mode = va_arg(va, mode_t);
|
||||||
va_end(va);
|
va_end(va);
|
||||||
|
|
||||||
lsi_maybe_init_unity3d(p);
|
lsi_maybe_init_unity3d(&lsi_table, p);
|
||||||
|
|
||||||
/* Not interested in this guy apparently */
|
/* Not interested in this guy apparently */
|
||||||
if (!lsi_override) {
|
if (!lsi_override) {
|
||||||
@@ -555,70 +316,6 @@ fallback_open:
|
|||||||
return lsi_table.open(p, flags, mode);
|
return lsi_table.open(p, flags, mode);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Get the shm file as a FILE stream
|
|
||||||
*/
|
|
||||||
static FILE *lsi_unity_get_config_file(const char *modes)
|
|
||||||
{
|
|
||||||
int perm = O_RDONLY;
|
|
||||||
|
|
||||||
if (strstr(modes, "w")) {
|
|
||||||
perm = O_RDWR | O_CREAT | O_TRUNC;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Attempt to shm_open our fake path */
|
|
||||||
int fd = shm_open(lsi_table.unity3d.shm_path, perm, 0666);
|
|
||||||
if (!fd) {
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
return fdopen(fd, modes);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* We now need to initialise the unity3d config if we haven't done so
|
|
||||||
*/
|
|
||||||
static void lsi_unity_init_config(void)
|
|
||||||
{
|
|
||||||
autofree(FILE) *source = NULL;
|
|
||||||
autofree(FILE) *dest = NULL;
|
|
||||||
|
|
||||||
if (lsi_table.unity3d.had_init || lsi_table.unity3d.failed) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
lsi_table.unity3d.had_init = true;
|
|
||||||
|
|
||||||
dest = lsi_unity_get_config_file("w");
|
|
||||||
source = lsi_table.fopen64(lsi_table.unity3d.original_config_path, "r");
|
|
||||||
|
|
||||||
lsi_unity_trim_copy_config(source, dest);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Redirect requests for non-existant config files in Unity3D to a temporary
|
|
||||||
* shm file which we'll write our initial "sane" configuration to.
|
|
||||||
*/
|
|
||||||
static FILE *lsi_unity_redirect(const char *p, const char *modes)
|
|
||||||
{
|
|
||||||
FILE *ret = NULL;
|
|
||||||
|
|
||||||
/* Preserve this path for later cloning.. */
|
|
||||||
lsi_table.unity3d.original_config_path = strdup(p);
|
|
||||||
|
|
||||||
lsi_unity_init_config();
|
|
||||||
|
|
||||||
ret = lsi_unity_get_config_file(modes);
|
|
||||||
if (!ret) {
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
lsi_log_info("fopen64(%s): Redirecting unity config '%s' to shm(%s)",
|
|
||||||
modes,
|
|
||||||
p,
|
|
||||||
lsi_table.unity3d.shm_path);
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
_nica_public_ FILE *fopen64(const char *p, const char *modes)
|
_nica_public_ FILE *fopen64(const char *p, const char *modes)
|
||||||
{
|
{
|
||||||
LsiRedirectOperation op = LSI_OPERATION_OPEN;
|
LsiRedirectOperation op = LSI_OPERATION_OPEN;
|
||||||
@@ -629,7 +326,7 @@ _nica_public_ FILE *fopen64(const char *p, const char *modes)
|
|||||||
*/
|
*/
|
||||||
lsi_redirect_init_tables();
|
lsi_redirect_init_tables();
|
||||||
|
|
||||||
lsi_maybe_init_unity3d(p);
|
lsi_maybe_init_unity3d(&lsi_table, p);
|
||||||
|
|
||||||
/* Not interested in this guy apparently */
|
/* Not interested in this guy apparently */
|
||||||
if (!lsi_override) {
|
if (!lsi_override) {
|
||||||
@@ -643,12 +340,42 @@ _nica_public_ FILE *fopen64(const char *p, const char *modes)
|
|||||||
|
|
||||||
fallback_open:
|
fallback_open:
|
||||||
|
|
||||||
if (is_unity3d_prefs_file(p)) {
|
if (is_unity3d_prefs_file(&lsi_table, p)) {
|
||||||
return lsi_unity_redirect(p, modes);
|
return lsi_unity_redirect(&lsi_table, p, modes);
|
||||||
}
|
}
|
||||||
return lsi_table.fopen64(p, modes);
|
return lsi_table.fopen64(p, modes);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef HAVE_SNAPD_SUPPORT
|
||||||
|
|
||||||
|
#include <unistd.h>
|
||||||
|
|
||||||
|
_nica_public_ struct passwd *getpwuid(uid_t uid)
|
||||||
|
{
|
||||||
|
/* Must ensure we're **really** initialised, as we might see open happen
|
||||||
|
* before the constructor..
|
||||||
|
*/
|
||||||
|
lsi_redirect_init_tables();
|
||||||
|
|
||||||
|
struct passwd *ret = NULL;
|
||||||
|
const char *snap_root = getenv("SNAP_USER_COMMON");
|
||||||
|
|
||||||
|
/* If they're requesting our uid and SNAP_USER_COMMON is set, then
|
||||||
|
* let us override the home directory to be correct.
|
||||||
|
*/
|
||||||
|
ret = lsi_table.getpwuid(uid);
|
||||||
|
if (!ret) {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (uid == getuid() && snap_root && *snap_root) {
|
||||||
|
ret->pw_dir = (char *)snap_root;
|
||||||
|
}
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Editor modelines - https://www.wireshark.org/tools/modelines.html
|
* Editor modelines - https://www.wireshark.org/tools/modelines.html
|
||||||
*
|
*
|
||||||
|
|||||||
@@ -11,6 +11,7 @@ if with_libredirect == true
|
|||||||
'profile.c',
|
'profile.c',
|
||||||
'profiles/ark.c',
|
'profiles/ark.c',
|
||||||
'profiles/project_highrise.c',
|
'profiles/project_highrise.c',
|
||||||
|
'unity.c',
|
||||||
]
|
]
|
||||||
|
|
||||||
sym_map = join_paths(meson.current_source_dir(), 'sym.map')
|
sym_map = join_paths(meson.current_source_dir(), 'sym.map')
|
||||||
|
|||||||
@@ -0,0 +1,83 @@
|
|||||||
|
/*
|
||||||
|
* This file is part of linux-steam-integration.
|
||||||
|
*
|
||||||
|
* Copyright © 2017 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
*
|
||||||
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
|
* published by the Free Software Foundation; either version 2.1
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <stdbool.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
#include "config.h"
|
||||||
|
|
||||||
|
#ifdef HAVE_SNAPD_SUPPORT
|
||||||
|
#include <pwd.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle definitions
|
||||||
|
*/
|
||||||
|
typedef int (*lsi_open_file)(const char *p, int flags, mode_t mode);
|
||||||
|
|
||||||
|
typedef FILE *(*lsi_fopen64_file)(const char *p, const char *modes);
|
||||||
|
|
||||||
|
#ifdef HAVE_SNAPD_SUPPORT
|
||||||
|
typedef struct passwd *(*lsi_getpwuid)(uid_t uid);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Global storage of handles for nicer organisation.
|
||||||
|
*/
|
||||||
|
typedef struct LsiRedirectTable {
|
||||||
|
lsi_open_file open;
|
||||||
|
lsi_fopen64_file fopen64;
|
||||||
|
|
||||||
|
#ifdef HAVE_SNAPD_SUPPORT
|
||||||
|
lsi_getpwuid getpwuid;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/* Allow future handle opens.. */
|
||||||
|
struct {
|
||||||
|
void *libc;
|
||||||
|
} handles;
|
||||||
|
|
||||||
|
/* Our shm_open() unity3d redirect.. */
|
||||||
|
struct {
|
||||||
|
char *original_config_path;
|
||||||
|
char *config_path;
|
||||||
|
char *shm_path;
|
||||||
|
bool enabled;
|
||||||
|
bool failed;
|
||||||
|
bool had_init;
|
||||||
|
} unity3d;
|
||||||
|
} LsiRedirectTable;
|
||||||
|
|
||||||
|
void lsi_unity_startup(LsiRedirectTable *lsi_table);
|
||||||
|
void lsi_unity_cleanup(LsiRedirectTable *lsi_table);
|
||||||
|
|
||||||
|
/* API Definitions for Unity handlers */
|
||||||
|
void lsi_maybe_init_unity3d(LsiRedirectTable *lsi_table, const char *p);
|
||||||
|
void lsi_unity_backup_config(LsiRedirectTable *lsi_table);
|
||||||
|
FILE *lsi_unity_redirect(LsiRedirectTable *lsi_table, const char *p, const char *modes);
|
||||||
|
FILE *lsi_unity_get_config_file(LsiRedirectTable *lsi_table, const char *modes);
|
||||||
|
void lsi_unity_trim_copy_config(FILE *from, FILE *to);
|
||||||
|
bool is_unity3d_prefs_file(LsiRedirectTable *lsi_table, const char *p);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Editor modelines - https://www.wireshark.org/tools/modelines.html
|
||||||
|
*
|
||||||
|
* Local variables:
|
||||||
|
* c-basic-offset: 8
|
||||||
|
* tab-width: 8
|
||||||
|
* indent-tabs-mode: nil
|
||||||
|
* End:
|
||||||
|
*
|
||||||
|
* vi: set shiftwidth=8 tabstop=8 expandtab:
|
||||||
|
* :indentSize=8:tabSize=8:noTabs=true:
|
||||||
|
*/
|
||||||
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
@@ -63,7 +64,7 @@ void lsi_redirect_profile_insert_rule(LsiRedirectProfile *self, LsiRedirect *red
|
|||||||
default:
|
default:
|
||||||
lsi_log_error("Attempted insert of unknown rule into '%s'", self->name);
|
lsi_log_error("Attempted insert of unknown rule into '%s'", self->name);
|
||||||
lsi_redirect_free(redirect);
|
lsi_redirect_free(redirect);
|
||||||
break;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Set head or prepend the rule */
|
/* Set head or prepend the rule */
|
||||||
|
|||||||
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
|
|||||||
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
{
|
{
|
||||||
global:
|
global:
|
||||||
fopen64;
|
fopen64;
|
||||||
|
getpwuid;
|
||||||
open;
|
open;
|
||||||
local:
|
local:
|
||||||
*;
|
*;
|
||||||
|
|||||||
@@ -0,0 +1,333 @@
|
|||||||
|
/*
|
||||||
|
* This file is part of linux-steam-integration.
|
||||||
|
*
|
||||||
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
|
*
|
||||||
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
|
* published by the Free Software Foundation; either version 2.1
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define _GNU_SOURCE
|
||||||
|
|
||||||
|
#include <errno.h>
|
||||||
|
#include <fcntl.h>
|
||||||
|
#include <stdbool.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <sys/mman.h>
|
||||||
|
#include <sys/stat.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
|
||||||
|
#include "../common/files.h"
|
||||||
|
#include "../common/log.h"
|
||||||
|
#include "nica/util.h"
|
||||||
|
|
||||||
|
#include "private.h"
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Cheap and cheerful, this is our default fake unity3d config which we write
|
||||||
|
* out to trick unity3d games into reading a non broken config on Linux.
|
||||||
|
* This forces the equivalent of "-screen-fullscreen 0" because the older
|
||||||
|
* Unity builds will set fullscreen to 1, but they'll also set the resolution
|
||||||
|
* width and height to 0 (which is then clamped)
|
||||||
|
*/
|
||||||
|
static const char *unity3d_config =
|
||||||
|
"\
|
||||||
|
<unity_prefs version_major=\"1\" version_minor=\"1\">\n\
|
||||||
|
<pref name=\"Screenmanager Is Fullscreen mode\" type=\"int\">0</pref>\n\
|
||||||
|
</unity_prefs>\n\
|
||||||
|
";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* When we rewrite the config file in place we'll repllace the "Is Fullscreen mode"
|
||||||
|
* line with this one so that we forcibly disable it.
|
||||||
|
*/
|
||||||
|
static const char *unity3d_snippet =
|
||||||
|
" <pref name=\"Screenmanager Is Fullscreen mode\" type=\"int\">0</pref>\n";
|
||||||
|
|
||||||
|
static inline bool str_has_prefix(const char *a, const char *b)
|
||||||
|
{
|
||||||
|
size_t lena, lenb;
|
||||||
|
lena = strlen(a);
|
||||||
|
lenb = strlen(b);
|
||||||
|
if (lenb > lena) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return strncmp(a, b, lenb) == 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The unity3d config path has been accessed, so we need to turn on our
|
||||||
|
* workaround for unity3d prefs
|
||||||
|
*/
|
||||||
|
void lsi_maybe_init_unity3d(LsiRedirectTable *lsi_table, const char *p)
|
||||||
|
{
|
||||||
|
if (lsi_table->unity3d.enabled) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!lsi_table->unity3d.config_path) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!str_has_prefix(p, lsi_table->unity3d.config_path)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Set by the main shim */
|
||||||
|
if (!getenv("LSI_USE_UNITY_HACK")) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* We're in action */
|
||||||
|
lsi_table->unity3d.enabled = true;
|
||||||
|
lsi_log_set_id("unity3d");
|
||||||
|
lsi_log_info("Activating \"black screen of nope\" workaround");
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Determine if the input path is a unity3d "prefs" file
|
||||||
|
*/
|
||||||
|
bool is_unity3d_prefs_file(LsiRedirectTable *lsi_table, const char *p)
|
||||||
|
{
|
||||||
|
autofree(char) *clone = NULL;
|
||||||
|
char *basenom = NULL;
|
||||||
|
|
||||||
|
/* Must only happen when enabled */
|
||||||
|
if (!lsi_table->unity3d.enabled) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* We found it already */
|
||||||
|
if (lsi_table->unity3d.original_config_path) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Must be in config path */
|
||||||
|
if (!str_has_prefix(p, lsi_table->unity3d.config_path)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
clone = strdup(p);
|
||||||
|
if (!clone) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
basenom = basename(clone);
|
||||||
|
if (!basenom) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Must be called "prefs" */
|
||||||
|
return strcmp(basenom, "prefs") == 0 ? true : false;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Copy the config from the @from file to the @to file, which
|
||||||
|
* will also strip out any "evil" lines, i.e. the fullscreen
|
||||||
|
* stanza.
|
||||||
|
*
|
||||||
|
* If the input file does not exist, the default configuration
|
||||||
|
* will be used.
|
||||||
|
*/
|
||||||
|
void lsi_unity_trim_copy_config(FILE *from, FILE *to)
|
||||||
|
{
|
||||||
|
char *buf = NULL;
|
||||||
|
size_t sn = 0;
|
||||||
|
ssize_t r = 0;
|
||||||
|
|
||||||
|
/* No input? Write the default configuration then */
|
||||||
|
if (!from) {
|
||||||
|
if (fwrite(unity3d_config, strlen(unity3d_config), 1, to) != 1) {
|
||||||
|
lsi_log_error("Failed to create initial Unity3D config: %s",
|
||||||
|
strerror(errno));
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Have an input file, write to the output but omit all the bad lines */
|
||||||
|
while ((r = getline(&buf, &sn, from)) != -1) {
|
||||||
|
const char *to_write = NULL;
|
||||||
|
|
||||||
|
/* Rewrite this line, it breaks games. */
|
||||||
|
if (strstr(buf, "Screenmanager Is Fullscreen mode")) {
|
||||||
|
to_write = unity3d_snippet;
|
||||||
|
r = strlen(to_write);
|
||||||
|
} else {
|
||||||
|
to_write = buf;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (fwrite(to_write, r, 1, to) != 1) {
|
||||||
|
lsi_log_error("Failed to write Unity3D config: %s", strerror(errno));
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (buf) {
|
||||||
|
free(buf);
|
||||||
|
buf = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fflush(to);
|
||||||
|
|
||||||
|
failed:
|
||||||
|
if (buf) {
|
||||||
|
free(buf);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Clone the existing shm configuration into the real config path, and copy
|
||||||
|
* all lines that we "like"
|
||||||
|
*
|
||||||
|
* Basically this ensures we force the dumped config to omit the fullscreen
|
||||||
|
* options as they break so many games.
|
||||||
|
*/
|
||||||
|
void lsi_unity_backup_config(LsiRedirectTable *lsi_table)
|
||||||
|
{
|
||||||
|
autofree(FILE) *shm_file = NULL;
|
||||||
|
autofree(FILE) *dest_file = NULL;
|
||||||
|
|
||||||
|
if (!lsi_table->unity3d.enabled || !lsi_table->unity3d.original_config_path) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
shm_file = lsi_unity_get_config_file(lsi_table, "r");
|
||||||
|
if (!shm_file) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
dest_file = lsi_table->fopen64(lsi_table->unity3d.original_config_path, "w");
|
||||||
|
if (!dest_file) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
lsi_log_debug("Saved Unity3D config to %s", lsi_table->unity3d.original_config_path);
|
||||||
|
lsi_unity_trim_copy_config(shm_file, dest_file);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the shm file as a FILE stream
|
||||||
|
*/
|
||||||
|
FILE *lsi_unity_get_config_file(LsiRedirectTable *lsi_table, const char *modes)
|
||||||
|
{
|
||||||
|
int perm = O_RDONLY;
|
||||||
|
|
||||||
|
if (strstr(modes, "w")) {
|
||||||
|
perm = O_RDWR | O_CREAT | O_TRUNC;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Attempt to shm_open our fake path */
|
||||||
|
int fd = shm_open(lsi_table->unity3d.shm_path, perm, 0666);
|
||||||
|
if (!fd) {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
return fdopen(fd, modes);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* We now need to initialise the unity3d config if we haven't done so
|
||||||
|
*/
|
||||||
|
static void lsi_unity_init_config(LsiRedirectTable *lsi_table)
|
||||||
|
{
|
||||||
|
autofree(FILE) *source = NULL;
|
||||||
|
autofree(FILE) *dest = NULL;
|
||||||
|
|
||||||
|
if (lsi_table->unity3d.had_init || lsi_table->unity3d.failed) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
lsi_table->unity3d.had_init = true;
|
||||||
|
|
||||||
|
dest = lsi_unity_get_config_file(lsi_table, "w");
|
||||||
|
source = lsi_table->fopen64(lsi_table->unity3d.original_config_path, "r");
|
||||||
|
|
||||||
|
lsi_unity_trim_copy_config(source, dest);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Redirect requests for non-existant config files in Unity3D to a temporary
|
||||||
|
* shm file which we'll write our initial "sane" configuration to.
|
||||||
|
*/
|
||||||
|
FILE *lsi_unity_redirect(LsiRedirectTable *lsi_table, const char *p, const char *modes)
|
||||||
|
{
|
||||||
|
FILE *ret = NULL;
|
||||||
|
|
||||||
|
/* Preserve this path for later cloning.. */
|
||||||
|
lsi_table->unity3d.original_config_path = strdup(p);
|
||||||
|
|
||||||
|
lsi_unity_init_config(lsi_table);
|
||||||
|
|
||||||
|
ret = lsi_unity_get_config_file(lsi_table, modes);
|
||||||
|
if (!ret) {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
lsi_log_debug("fopen64(%s): Redirecting unity config '%s' to shm(%s)",
|
||||||
|
modes,
|
||||||
|
p,
|
||||||
|
lsi_table->unity3d.shm_path);
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set up any needed variables for future unity usage
|
||||||
|
*/
|
||||||
|
void lsi_unity_startup(LsiRedirectTable *lsi_table)
|
||||||
|
{
|
||||||
|
autofree(char) *xdg_config_dir = NULL;
|
||||||
|
|
||||||
|
/* Ensure we know the path to unity3d config */
|
||||||
|
xdg_config_dir = lsi_get_user_config_dir();
|
||||||
|
if (asprintf(&lsi_table->unity3d.config_path, "%s/unity3d", xdg_config_dir) < 0) {
|
||||||
|
fputs("OOM\n", stderr);
|
||||||
|
abort();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* shm path for our fake unity3d config path */
|
||||||
|
if (asprintf(&lsi_table->unity3d.shm_path,
|
||||||
|
"/u%d-LinuxSteamIntegration.unity3d.%d",
|
||||||
|
getuid(),
|
||||||
|
getpgrp()) < 0) {
|
||||||
|
fputs("OOM\n", stderr);
|
||||||
|
abort();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Symbolic, we don't just use this for anyone, yknow. :P */
|
||||||
|
lsi_table->unity3d.enabled = false;
|
||||||
|
lsi_table->unity3d.failed = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
void lsi_unity_cleanup(LsiRedirectTable *lsi_table)
|
||||||
|
{
|
||||||
|
if (lsi_table->unity3d.original_config_path) {
|
||||||
|
lsi_unity_backup_config(lsi_table);
|
||||||
|
free(lsi_table->unity3d.original_config_path);
|
||||||
|
lsi_table->unity3d.original_config_path = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (lsi_table->unity3d.config_path) {
|
||||||
|
free(lsi_table->unity3d.config_path);
|
||||||
|
lsi_table->unity3d.config_path = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (lsi_table->unity3d.shm_path) {
|
||||||
|
(void)shm_unlink(lsi_table->unity3d.shm_path);
|
||||||
|
free(lsi_table->unity3d.shm_path);
|
||||||
|
lsi_table->unity3d.shm_path = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Editor modelines - https://www.wireshark.org/tools/modelines.html
|
||||||
|
*
|
||||||
|
* Local variables:
|
||||||
|
* c-basic-offset: 8
|
||||||
|
* tab-width: 8
|
||||||
|
* indent-tabs-mode: nil
|
||||||
|
* End:
|
||||||
|
*
|
||||||
|
* vi: set shiftwidth=8 tabstop=8 expandtab:
|
||||||
|
* :indentSize=8:tabSize=8:noTabs=true:
|
||||||
|
*/
|
||||||
+2
-1
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2016-2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
|
|||||||
+10
-1
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2016-2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
@@ -17,6 +18,7 @@
|
|||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
#include "../common/files.h"
|
#include "../common/files.h"
|
||||||
|
#include "config.h"
|
||||||
#include "lsi.h"
|
#include "lsi.h"
|
||||||
#include "shim.h"
|
#include "shim.h"
|
||||||
|
|
||||||
@@ -38,6 +40,8 @@ int main(int argc, char **argv)
|
|||||||
{
|
{
|
||||||
const char *operation_prefix = NULL;
|
const char *operation_prefix = NULL;
|
||||||
const char *steam_binary = NULL;
|
const char *steam_binary = NULL;
|
||||||
|
__attribute__((unused)) const char *tdir = NULL;
|
||||||
|
__attribute__((unused)) int dir_ret = 0;
|
||||||
|
|
||||||
if (!shim_bootstrap()) {
|
if (!shim_bootstrap()) {
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
@@ -45,6 +49,7 @@ int main(int argc, char **argv)
|
|||||||
|
|
||||||
#ifdef HAVE_SNAPD_SUPPORT
|
#ifdef HAVE_SNAPD_SUPPORT
|
||||||
operation_prefix = getenv("SNAP");
|
operation_prefix = getenv("SNAP");
|
||||||
|
tdir = getenv("SNAP_USER_COMMON");
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
steam_binary = shim_get_steam_binary(operation_prefix);
|
steam_binary = shim_get_steam_binary(operation_prefix);
|
||||||
@@ -54,6 +59,10 @@ int main(int argc, char **argv)
|
|||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (tdir) {
|
||||||
|
dir_ret = chdir(tdir);
|
||||||
|
}
|
||||||
|
|
||||||
return shim_execute(steam_binary, --argc, ++argv);
|
return shim_execute(steam_binary, --argc, ++argv);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -29,6 +29,7 @@ if shim_behaviour != 'none'
|
|||||||
link_lsi,
|
link_lsi,
|
||||||
],
|
],
|
||||||
install: true,
|
install: true,
|
||||||
|
install_dir: path_bindir,
|
||||||
)
|
)
|
||||||
|
|
||||||
lsi_exec = executable(
|
lsi_exec = executable(
|
||||||
@@ -39,5 +40,6 @@ if shim_behaviour != 'none'
|
|||||||
link_lsi,
|
link_lsi,
|
||||||
],
|
],
|
||||||
install: true,
|
install: true,
|
||||||
|
install_dir: path_bindir,
|
||||||
)
|
)
|
||||||
endif
|
endif
|
||||||
|
|||||||
+20
-22
@@ -1,7 +1,8 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of linux-steam-integration.
|
* This file is part of linux-steam-integration.
|
||||||
*
|
*
|
||||||
* Copyright © 2016-2017 Ikey Doherty <ikey@solus-project.com>
|
* Copyright © 2016-2018 Ikey Doherty <ikey@solus-project.com>
|
||||||
|
* Copyright © 2018-2019 Intel Corporation
|
||||||
*
|
*
|
||||||
* linux-steam-integration is free software; you can redistribute it and/or
|
* linux-steam-integration is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Lesser General Public License as
|
* modify it under the terms of the GNU Lesser General Public License as
|
||||||
@@ -26,24 +27,18 @@
|
|||||||
#include "lsi.h"
|
#include "lsi.h"
|
||||||
#include "shim.h"
|
#include "shim.h"
|
||||||
|
|
||||||
/**
|
|
||||||
* Required to force Steam into 32-bit detection mode, which is useful for
|
|
||||||
* recent issues like the CS:GO 64-bit update with huge FPS drops
|
|
||||||
*/
|
|
||||||
#define EMUL32BIN "linux32"
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Audit path is used for the libintercept library to ensure Steam only uses the
|
* Audit path is used for the libintercept library to ensure Steam only uses the
|
||||||
* host SDL, etc.
|
* host SDL, etc.
|
||||||
*/
|
*/
|
||||||
#define AUDIT_PATH "/usr/\$LIB/liblsi-intercept.so"
|
#define AUDIT_PATH "/usr/$LIB/liblsi-intercept.so"
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Redirect path is used for the libredirect library to perform internal
|
* Redirect path is used for the libredirect library to perform internal
|
||||||
* redirections in functions like `open()` where needed to hotfix games
|
* redirections in functions like `open()` where needed to hotfix games
|
||||||
* at runtime.
|
* at runtime.
|
||||||
*/
|
*/
|
||||||
#define REDIRECT_PATH "/usr/\$LIB/liblsi-redirect.so"
|
#define REDIRECT_PATH "/usr/$LIB/liblsi-redirect.so"
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Potential for the host Vulkan ICD files (old vs new)
|
* Potential for the host Vulkan ICD files (old vs new)
|
||||||
@@ -188,11 +183,9 @@ static void shim_export_extra(const char *prefix)
|
|||||||
* This allows us to handle the special-case multiarch mounts.
|
* This allows us to handle the special-case multiarch mounts.
|
||||||
*/
|
*/
|
||||||
static const char *ld_library_dirs[] = {
|
static const char *ld_library_dirs[] = {
|
||||||
"/var/lib/snapd/lib/gl/vdpau", /**<64-bit vdpau */
|
"/var/lib/snapd/lib/gl/vdpau", /**<64-bit vdpau */
|
||||||
"/var/lib/snapd/lib/gl32/vdpau", /**<32bit vdpau */
|
"/var/lib/snapd/lib/gl32/vdpau", /**<32bit vdpau */
|
||||||
"/usr/lib/glx-provider/default", /**<Solus mesa, 64-bit */
|
"/var/lib/snapd/lib/gl", /**<Potential host NVIDIA libraries */
|
||||||
"/usr/lib32/glx-provider/default", /**<Solus mesa, 32bit */
|
|
||||||
"/var/lib/snapd/lib/gl", /**<Potential host NVIDIA libraries */
|
|
||||||
"/var/lib/snapd/lib/gl32", /**<Potential host NVIDIA 32-bit libraries (new location) */
|
"/var/lib/snapd/lib/gl32", /**<Potential host NVIDIA 32-bit libraries (new location) */
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -229,6 +222,9 @@ static void shim_export_extra(const char *prefix)
|
|||||||
shim_export_merge_vars("PATH", prefix, "/usr/bin");
|
shim_export_merge_vars("PATH", prefix, "/usr/bin");
|
||||||
shim_export_merge_vars("PATH", prefix, "/bin");
|
shim_export_merge_vars("PATH", prefix, "/bin");
|
||||||
|
|
||||||
|
/* We require our PulseAudio fake script to be seen first. */
|
||||||
|
shim_export_merge_vars("PATH", prefix, FAKE_SCRIPTS_DIR "/pulseaudio");
|
||||||
|
|
||||||
/* Try both known Vulkan ICD paths */
|
/* Try both known Vulkan ICD paths */
|
||||||
if (!shim_init_vulkan(VK_GLOB_2)) {
|
if (!shim_init_vulkan(VK_GLOB_2)) {
|
||||||
shim_init_vulkan(VK_GLOB);
|
shim_init_vulkan(VK_GLOB);
|
||||||
@@ -342,22 +338,24 @@ bool shim_bootstrap()
|
|||||||
static int shim_execute_internal(const char *command, int argc, char **argv, bool use_path)
|
static int shim_execute_internal(const char *command, int argc, char **argv, bool use_path)
|
||||||
{
|
{
|
||||||
bool is_x86_64;
|
bool is_x86_64;
|
||||||
const char *n_argv[argc + 3];
|
const char *n_argv[argc + 5];
|
||||||
const char *exec_command = NULL;
|
const char *exec_command = NULL;
|
||||||
int i = 1;
|
int i = 1;
|
||||||
int8_t off = 1;
|
int8_t off = 1;
|
||||||
int (*vfunc)(const char *, char *const argv[]) = NULL;
|
int (*vfunc)(const char *, char *const argv[]) = NULL;
|
||||||
|
|
||||||
is_x86_64 = lsi_system_is_64bit();
|
is_x86_64 = lsi_system_is_64bit();
|
||||||
memset(&n_argv, 0, sizeof(char *) * (argc + 3));
|
memset(&n_argv, 0, sizeof(char *) * (argc + 5));
|
||||||
|
|
||||||
/* If we're 64-bit and 32-bit is forced, proxy via linux32 */
|
/* If we're 64-bit and 32-bit is forced, proxy via setarch linux32 */
|
||||||
if (lsi_config.force_32 && is_x86_64) {
|
if (lsi_config.force_32 && is_x86_64) {
|
||||||
exec_command = EMUL32BIN;
|
exec_command = "setarch";
|
||||||
n_argv[0] = EMUL32BIN;
|
n_argv[0] = "setarch";
|
||||||
n_argv[1] = command;
|
n_argv[1] = "linux32";
|
||||||
off = 2;
|
n_argv[2] = "--";
|
||||||
/* Use linux32 in the path */
|
n_argv[3] = command;
|
||||||
|
off = 4;
|
||||||
|
/* Use setarch in the path */
|
||||||
vfunc = execvp;
|
vfunc = execvp;
|
||||||
} else {
|
} else {
|
||||||
/* Directly call lsi_exec_bin */
|
/* Directly call lsi_exec_bin */
|
||||||
|
|||||||
Reference in New Issue
Block a user