Skip to content

Commit 3bbe32a

Browse files
committed
Make SteamAPI intialization more robust
1 parent e9c2927 commit 3bbe32a

5 files changed

Lines changed: 86 additions & 7 deletions

File tree

SEToolbox/Interop/SpaceEngineersCore.cs

Lines changed: 77 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@
1717
using SEToolbox.Models;
1818
using SEToolbox.Support;
1919
using SpaceEngineers.Game;
20+
using Steamworks;
2021
using VRage;
2122
using VRage.Collections;
2223
using VRage.FileSystem;
@@ -111,7 +112,7 @@ public SpaceEngineersCore()
111112
// This will start the Steam Service, and Steam will think SE is running.
112113
// TODO: we don't want to be doing this all the while SEToolbox is running,
113114
// perhaps a once off during load to fetch of mods then disconnect/Dispose.
114-
_steamService = MySteamGameService.Create(Sandbox.Engine.Platform.Game.IsDedicated, AppId);
115+
_steamService = CreateSteamService();
115116
MyServiceManager.Instance.AddService(_steamService);
116117

117118
Log.Debug("Init VRage platform.");
@@ -194,6 +195,81 @@ public SpaceEngineersCore()
194195
_manageDeleteVoxelList = [];
195196
}
196197

198+
// Re-implement most of MySteamService constructor (with adjustments) to
199+
// bypass the call to Environment.Exit
200+
static IMyGameService CreateSteamService()
201+
{
202+
//return MySteamGameService.Create(Sandbox.Engine.Platform.Game.IsDedicated, AppId);
203+
204+
var appIdStr = AppId.ToString();
205+
Environment.SetEnvironmentVariable("SteamAppId", appIdStr);
206+
Environment.SetEnvironmentVariable("SteamGameId", appIdStr);
207+
208+
// isDedicated: true skips the initialization that is done here instead.
209+
var service = MySteamGameService.Create(isDedicated: true, AppId);
210+
var serviceType = service.GetType();
211+
212+
var steamAppId = (AppId_t)AppId;
213+
214+
//if (SteamAPI.RestartAppIfNecessary(steamAppId))
215+
// Log.Error("SteamAPI.RestartAppIfNecessary returned true.");
216+
217+
bool isActive = SteamAPI.Init();
218+
serviceType.GetProperty("IsActive").SetValue(service, isActive);
219+
220+
if (!isActive)
221+
Log.Error("Failed to initialize Steam service.");
222+
223+
IMyInventoryService serviceInstance;
224+
225+
const ulong OFFLINE_STEAM_ID = 1234567891011uL;
226+
227+
if (isActive)
228+
{
229+
var steamUserId = SteamUser.GetSteamID();
230+
service.UserId = (ulong)steamUserId;
231+
232+
var userName = "\ue030" + SteamFriends.GetPersonaName();
233+
var hasLicenseResult = SteamUser.UserHasLicenseForApp(steamUserId, steamAppId);
234+
bool ownsGame = hasLicenseResult == EUserHasLicenseForAppResult.k_EUserHasLicenseResultHasLicense;
235+
var userUniverse = (MyGameServiceUniverse)SteamUtils.GetConnectedUniverse();
236+
var branchName = SteamApps.GetCurrentBetaName(out var pchName, 512) ? pchName : "default";
237+
238+
serviceType.GetField("SteamUserId", BindingFlags.Instance | BindingFlags.NonPublic).SetValue(service, steamUserId);
239+
serviceType.GetProperty("UserName").SetValue(service, userName);
240+
serviceType.GetProperty("OwnsGame").SetValue(service, ownsGame);
241+
serviceType.GetProperty("UserUniverse").SetValue(service, userUniverse);
242+
serviceType.GetProperty("BranchName").SetValue(service, branchName);
243+
244+
SteamUserStats.RequestCurrentStats();
245+
serviceType.GetMethod("RegisterCallbacks", BindingFlags.Instance | BindingFlags.NonPublic).Invoke(service, []);
246+
247+
var remoteStorage = Activator.CreateInstance(Type.GetType("VRage.Steam.MySteamRemoteStorage, VRage.Steam"));
248+
249+
serviceType.GetField("m_remoteStorage", BindingFlags.Instance | BindingFlags.NonPublic).SetValue(service, remoteStorage);
250+
251+
serviceInstance = (IMyInventoryService)Activator.CreateInstance(Type.GetType("VRage.Steam.MySteamInventory, VRage.Steam"), [service]);
252+
}
253+
else
254+
{
255+
service.UserId = OFFLINE_STEAM_ID;
256+
serviceInstance = new MyNullInventoryService();
257+
}
258+
259+
MyServiceManager.Instance.AddService(serviceInstance);
260+
261+
if (!isActive)
262+
{
263+
var errMsg = """
264+
Failed to initialize Steam API. Please ensure Steam is running and re-launch SEToolbox.
265+
You can try to continue anyway but modded worlds may not work correctly.
266+
""";
267+
MessageBox.Show(errMsg, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
268+
}
269+
270+
return service;
271+
}
272+
197273
static void InitMultithreading()
198274
{
199275
//MySandboxGame.InitMultithreading();

SEToolbox/Interop/SpaceEngineersWorkshop.cs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,9 @@ public class SpaceEngineersWorkshop
1414
{
1515
public static MyWorkshop.ResultData DownloadWorldModsBlocking(List<MyObjectBuilder_Checkpoint.ModItem> mods, MyWorkshop.CancelToken cancelToken)
1616
{
17+
if (!MyGameService.IsActive)
18+
return default;
19+
1720
MyWorkshop.ResultData ret = default;
1821

1922
Task task = Parallel.Start(() =>

SEToolbox/Models/WorldResource.cs

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -287,9 +287,13 @@ public void LoadDefinitionsAndMods()
287287
if (_resources == null || Checkpoint == null || Checkpoint.Mods == null)
288288
return;
289289

290-
SpaceEngineersWorkshop.DownloadWorldModsBlocking(Checkpoint.Mods, cancelToken: null);
290+
List<MyObjectBuilder_Checkpoint.ModItem> mods = [.. Checkpoint.Mods];
291+
var result = SpaceEngineersWorkshop.DownloadWorldModsBlocking(mods, cancelToken: null);
291292

292-
_resources.LoadDefinitionsAndMods(DataPath.ModsPath, Checkpoint.Mods);
293+
if (result.Result == 0)
294+
mods.Clear();
295+
296+
_resources.LoadDefinitionsAndMods(DataPath.ModsPath, mods);
293297
}
294298

295299
public bool LoadSector(out string errorInformation, bool snapshot = false)

SEToolbox/SEToolbox.csproj

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -125,9 +125,6 @@
125125
<Link>VRage.Native.dll</Link>
126126
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
127127
</Content>
128-
<None Include="steam_appid.txt">
129-
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
130-
</None>
131128
</ItemGroup>
132129

133130
<ItemGroup>

SEToolbox/steam_appid.txt

Lines changed: 0 additions & 1 deletion
This file was deleted.

0 commit comments

Comments
 (0)