static string GetAppOrDepotName(Steam3Session steam3, uint depotId, uint appId) { if (depotId == INVALID_DEPOT_ID) { KeyValue info = GetSteam3AppSection(steam3, appId, EAppInfoSection.Common); if (info == null) { return(String.Empty); } return(info["name"].AsString()); } else { KeyValue depots = GetSteam3AppSection(steam3, appId, EAppInfoSection.Depots); if (depots == null) { return(String.Empty); } KeyValue depotChild = depots[depotId.ToString()]; if (depotChild == null) { return(String.Empty); } return(depotChild["name"].AsString()); } }
static uint GetSteam3AppBuildNumber(Steam3Session steam3, uint appId, string branch) { if (appId == INVALID_APP_ID) { return(0); } KeyValue depots = ContentDownloader.GetSteam3AppSection(steam3, appId, EAppInfoSection.Depots); KeyValue branches = depots["branches"]; KeyValue node = branches[branch]; if (node == KeyValue.Invalid) { return(0); } KeyValue buildid = node["buildid"]; if (buildid == KeyValue.Invalid) { return(0); } return(uint.Parse(buildid.Value)); }
public static bool InitializeSteam3(string username = null, string password = null) { string loginKey = null; if (username != null && Config.RememberPassword) { _ = AccountSettingsStore.Instance.LoginKeys.TryGetValue(username, out loginKey); } Steam3 = new Steam3Session( new SteamUser.LogOnDetails() { Username = username, Password = loginKey == null ? password : null, ShouldRememberPassword = Config.RememberPassword, LoginKey = loginKey, LoginID = Config.LoginID ?? 0x534B32, // "SK2" } ); Steam3Credentials = Steam3.WaitForCredentials(); if (!Steam3Credentials.IsValid) { Console.WriteLine("Unable to get Steam3 credentials."); return(false); } cdnPool = new CDNClientPool(Steam3); return(true); }
public static async Task DownloadApp(Steam3Session steam3, string installPath, uint appId, bool manifestOnly = false, Action downloadCompleteAction = null, params string[] fileList) { //Config.CellID = 0; Config.UsingFileList = fileList != null && fileList.Length > 0; if (Config.UsingFileList) { Config.FilesToDownload = new List <string>(fileList); } Config.InstallDirectory = installPath; Config.DownloadManifestOnly = manifestOnly; Config.MaxDownloads = 4; Config.MaxServers = 20; string branch = DEFAULT_BRANCH; string os = "windows"; cdnPool = new CDNClientPool(steam3); try { await DownloadAppAsync(steam3, appId, INVALID_DEPOT_ID, INVALID_MANIFEST_ID, branch, os, false, downloadCompleteAction); } catch (Exception e) { DebugLog.WriteLine("ErrorContentDownloader", e.ToString()); } Shutdown(); }
public static bool InitializeSteam3(string username, string password) { string loginKey = null; if (username != null && Config.RememberPassword) { _ = ConfigStore.TheConfig.LoginKeys.TryGetValue(username, out loginKey); } steam3 = new Steam3Session( new SteamUser.LogOnDetails() { Username = username, Password = loginKey == null ? password : null, ShouldRememberPassword = Config.RememberPassword, LoginKey = loginKey, } ); steam3Credentials = steam3.WaitForCredentials(); if (!steam3Credentials.IsValid) { Console.WriteLine("Unable to get steam3 credentials."); return(false); } cdnPool = new CDNClientPool(steam3); return(true); }
public CDNClientPool(Steam3Session steamSession) { this.steamSession = steamSession; activeClientPool = new ConcurrentBag <CDNClient>(); activeClientAuthed = new ConcurrentDictionary <CDNClient, Tuple <uint, CDNClient.Server> >(); availableServerEndpoints = new BlockingCollection <CDNClient.Server>(); populatePoolEvent = new AutoResetEvent(true); monitorTask = Task.Factory.StartNew(ConnectionPoolMonitorAsync).Unwrap(); }
public CDNClientPool(Steam3Session steamSession) { this.steamSession = steamSession; CDNClient = new CDNClient(steamSession.steamClient); activeConnectionPool = new ConcurrentBag <CDNClient.Server>(); availableServerEndpoints = new BlockingCollection <CDNClient.Server>(); populatePoolEvent = new AutoResetEvent(true); shutdownToken = new CancellationTokenSource(); monitorTask = Task.Factory.StartNew(ConnectionPoolMonitorAsync).Unwrap(); }
public static async Task DownloadPubfileAsync(Steam3Session steam3, ulong publishedFileId, Action downloadCompleteAction = null) { var details = await steam3.GetPubfileDetails(publishedFileId); if (details.hcontent_file > 0) { await DownloadAppAsync(steam3, details.consumer_appid, details.consumer_appid, details.hcontent_file, DEFAULT_BRANCH, null, true, downloadCompleteAction); } else { DebugLog.WriteLine("ContentDownloader", "Unable to locate manifest ID for published file " + publishedFileId); } }
public CDNClientPool(Steam3Session steamSession) { this.steamSession = steamSession; activeClientPool = new ConcurrentBag <CDNClient>(); activeClientAuthed = new ConcurrentDictionary <CDNClient, Tuple <uint, CDNClient.Server> >(); availableServerEndpoints = new BlockingCollection <CDNClient.Server>(); populatePoolEvent = new AutoResetEvent(true); monitorThread = new Thread(ConnectionPoolMonitor); monitorThread.Name = "CDNClient Pool Monitor"; monitorThread.IsBackground = true; monitorThread.Start(); }
public static void InitializeSteam3(string username, string password) { steam3 = new Steam3Session( new SteamUser.LogOnDetails() { Username = username, Password = password, } ); steam3Credentials = steam3.WaitForCredentials(); if (!steam3Credentials.IsValid) { Console.WriteLine("Unable to get steam3 credentials."); return; } }
internal static KeyValue GetSteam3AppSection(Steam3Session steam3, uint appId, EAppInfoSection section) { if (steam3 == null || steam3.AppInfo == null) { return(null); } SteamApps.PICSProductInfoCallback.PICSProductInfo app; if (!steam3.AppInfo.TryGetValue(appId, out app) || app == null) { return(null); } KeyValue appinfo = app.KeyValues; string section_key; switch (section) { case EAppInfoSection.Common: section_key = "common"; break; case EAppInfoSection.Extended: section_key = "extended"; break; case EAppInfoSection.Config: section_key = "config"; break; case EAppInfoSection.Depots: section_key = "depots"; break; default: throw new NotImplementedException(); } KeyValue section_kv = appinfo.Children.Where(c => c.Name == section_key).FirstOrDefault(); return(section_kv); }
static async Task <bool> AccountHasAccess(Steam3Session steam3, uint depotId) { if (steam3 == null || steam3.steamUser.SteamID == null || (steam3.Licenses == null && steam3.steamUser.SteamID.AccountType != EAccountType.AnonUser)) { return(false); } IEnumerable <uint> licenseQuery; if (steam3.steamUser.SteamID.AccountType == EAccountType.AnonUser) { licenseQuery = new List <uint>() { 17906 }; } else { licenseQuery = steam3.Licenses.Select(x => x.PackageID); } await steam3.RequestPackageInfo(licenseQuery); foreach (var license in licenseQuery) { SteamApps.PICSProductInfoCallback.PICSProductInfo package; if (steam3.PackageInfo.TryGetValue(license, out package) && package != null) { if (package.KeyValues["appids"].Children.Any(child => child.AsUnsignedInteger() == depotId)) { return(true); } if (package.KeyValues["depotids"].Children.Any(child => child.AsUnsignedInteger() == depotId)) { return(true); } } } return(false); }
public static bool InitializeSteam3(string username, string password) { steam3 = new Steam3Session( new SteamUser.LogOnDetails() { Username = username, Password = password, } ); steam3Credentials = steam3.WaitForCredentials(); if (!steam3Credentials.IsValid) { Console.WriteLine("Unable to get steam3 credentials."); return false; } cdnPool = new CDNClientPool(steam3); return true; }
static async Task <ulong> GetSteam3DepotManifest(Steam3Session steam3, uint depotId, uint appId, string branch) { KeyValue depots = GetSteam3AppSection(steam3, appId, EAppInfoSection.Depots); KeyValue depotChild = depots[depotId.ToString()]; if (depotChild == KeyValue.Invalid) { return(INVALID_MANIFEST_ID); } // Shared depots can either provide manifests, or leave you relying on their parent app. // It seems that with the latter, "sharedinstall" will exist (and equals 2 in the one existance I know of). // Rather than relay on the unknown sharedinstall key, just look for manifests. Test cases: 111710, 346680. if (depotChild["manifests"] == KeyValue.Invalid && depotChild["depotfromapp"] != KeyValue.Invalid) { uint otherAppId = depotChild["depotfromapp"].AsUnsignedInteger(); if (otherAppId == appId) { // This shouldn't ever happen, but ya never know with Valve. Don't infinite loop. DebugLog.WriteLine("ContentDownloader", "App " + appId + ", Depot " + depotId + " has depotfromapp of " + otherAppId + "!"); return(INVALID_MANIFEST_ID); //return INVALID_MANIFEST_ID; } await steam3.RequestAppInfo(otherAppId); return(await GetSteam3DepotManifest(steam3, depotId, otherAppId, branch)); } var manifests = depotChild["manifests"]; var manifests_encrypted = depotChild["encryptedmanifests"]; if (manifests.Children.Count == 0 && manifests_encrypted.Children.Count == 0) { return(INVALID_MANIFEST_ID); } var node = manifests[branch]; if (branch != "Public" && node == KeyValue.Invalid) { var node_encrypted = manifests_encrypted[branch]; if (node_encrypted != KeyValue.Invalid) { string password = Config.BetaPassword; if (password == null) { Config.BetaPassword = password = Console.ReadLine(); } var encrypted_v1 = node_encrypted["encrypted_gid"]; var encrypted_v2 = node_encrypted["encrypted_gid_2"]; if (encrypted_v1 != KeyValue.Invalid) { byte[] input = Util.DecodeHexString(encrypted_v1.Value); byte[] manifest_bytes = CryptoHelper.VerifyAndDecryptPassword(input, password); if (manifest_bytes == null) { DebugLog.WriteLine("ContentDownloader", "Password was invalid for branch " + branch); return(INVALID_MANIFEST_ID); } return(BitConverter.ToUInt64(manifest_bytes, 0)); } else if (encrypted_v2 != KeyValue.Invalid) { // Submit the password to Steam now to get encryption keys await steam3.CheckAppBetaPassword(appId, Config.BetaPassword); if (!steam3.AppBetaPasswords.ContainsKey(branch)) { DebugLog.WriteLine("ContentDownloader", "Password was invalid for branch " + branch); return(INVALID_MANIFEST_ID); } byte[] input = Util.DecodeHexString(encrypted_v2.Value); byte[] manifest_bytes = null; try { manifest_bytes = CryptoHelper.SymmetricDecryptECB(input, steam3.AppBetaPasswords[branch]); } catch (Exception e) { DebugLog.WriteLine("ContentDownloader", "Failed to decrypt branch " + branch + ": " + e.Message); return(INVALID_MANIFEST_ID); } return(BitConverter.ToUInt64(manifest_bytes, 0)); } else { DebugLog.WriteLine("ContentDownloader", "Unhandled depot encryption for depotId " + depotId); return(INVALID_MANIFEST_ID); } } return(INVALID_MANIFEST_ID); } if (node.Value == null) { return(INVALID_MANIFEST_ID); } return(ulong.Parse(node.Value)); }
public static async Task DownloadAppAsync(Steam3Session steam3, uint appId, uint depotId, ulong manifestId, string branch, string os, bool isUgc, Action downloadCompleteAction = null) { if (steam3 != null) { await steam3.RequestAppInfo(appId); } bool hasAccess = await AccountHasAccess(steam3, appId); if (!hasAccess) { bool freeAppLicense = await steam3.RequestFreeAppLicense(appId); if (freeAppLicense) { DebugLog.WriteLine("ContentDownloader", "Obtained FreeOnDemand license for app " + appId); } else { string contentName = GetAppOrDepotName(steam3, INVALID_DEPOT_ID, appId); DebugLog.WriteLine("ContentDownloader", "App " + appId + " (" + contentName + ") is not available from this account."); return; } } var depotIDs = new List <uint>(); KeyValue depots = GetSteam3AppSection(steam3, appId, EAppInfoSection.Depots); if (isUgc) { var workshopDepot = depots["workshopdepot"].AsUnsignedInteger(); if (workshopDepot != 0) { depotId = workshopDepot; } depotIDs.Add(depotId); } else { DebugLog.WriteLine("ContentDownloader", "Using app branch: '" + branch + "'."); if (depots != null) { foreach (var depotSection in depots.Children) { uint id = INVALID_DEPOT_ID; if (depotSection.Children.Count == 0) { continue; } if (!uint.TryParse(depotSection.Name, out id)) { continue; } if (depotId != INVALID_DEPOT_ID && id != depotId) { continue; } if (depotId == INVALID_DEPOT_ID && !Config.DownloadAllPlatforms) { var depotConfig = depotSection["config"]; if (depotConfig != KeyValue.Invalid && depotConfig["oslist"] != KeyValue.Invalid && !string.IsNullOrWhiteSpace(depotConfig["oslist"].Value)) { var oslist = depotConfig["oslist"].Value.Split(','); if (Array.IndexOf(oslist, os ?? Util.GetSteamOS()) == -1) { continue; } } } depotIDs.Add(id); } } if (depotIDs == null || (depotIDs.Count == 0 && depotId == INVALID_DEPOT_ID)) { DebugLog.WriteLine("ContentDownloader", "Couldn't find any depots to download for app " + appId); return; } else if (depotIDs.Count == 0) { DebugLog.WriteLine("ContentDownloader", "Depot " + depotId + " not listed for app " + appId); return; } } var infos = new List <DepotDownloadInfo>(); foreach (var depot in depotIDs) { var info = await GetDepotInfo(steam3, depot, appId, manifestId, branch); if (info != null) { infos.Add(info); } } try { IsDownloading = true; await DownloadSteam3Async(appId, infos, downloadCompleteAction); } catch (OperationCanceledException) { DebugLog.WriteLine("ContentDownloader", "App " + appId + " was not completely downloaded."); } finally { DebugLog.WriteLine("ContentDownloader", "Download completed"); } }
public static void InitializeSteam3(string username, string password) { steam3 = new Steam3Session( new SteamUser.LogOnDetails() { Username = username, Password = password, RequestSteam2Ticket = true, } ); steam3Credentials = steam3.WaitForCredentials(); if (!steam3Credentials.IsValid) { Console.WriteLine("Unable to get steam3 credentials."); return; } }
static async Task <DepotDownloadInfo> GetDepotInfo(Steam3Session steam3, uint depotId, uint appId, ulong manifestId, string branch) { if (steam3 != null && appId != INVALID_APP_ID) { await steam3.RequestAppInfo(appId); } string contentName = GetAppOrDepotName(steam3, depotId, appId); bool hasAccess = await AccountHasAccess(steam3, depotId); if (!hasAccess) { DebugLog.WriteLine("ContentDownloader", "Depot " + depotId + " (" + contentName + ") is not available from this account."); return(null); } // Skip requesting an app ticket steam3.AppTickets[depotId] = null; if (manifestId == INVALID_MANIFEST_ID) { manifestId = await GetSteam3DepotManifest(steam3, depotId, appId, branch); if (manifestId == INVALID_MANIFEST_ID && branch != "public") { DebugLog.WriteLine("ContentDownloader", "Warning: Depot " + depotId + " does not have branch named \"" + branch + "\". Trying public branch."); branch = "public"; manifestId = await GetSteam3DepotManifest(steam3, depotId, appId, branch); } if (manifestId == INVALID_MANIFEST_ID) { DebugLog.WriteLine("ContentDownloader", "Depot " + depotId + " (" + contentName + ") missing public subsection or manifest section."); return(null); } } uint uVersion = GetSteam3AppBuildNumber(steam3, appId, branch); string installDir; if (!CreateDirectories(depotId, uVersion, out installDir)) { DebugLog.WriteLine("ContentDownloader", "Error: Unable to create install directories!"); return(null); } await steam3.RequestDepotKey(depotId, appId); if (!steam3.DepotKeys.ContainsKey(depotId)) { DebugLog.WriteLine("ContentDownloader", "No valid depot key for " + depotId + ", unable to download."); return(null); } byte[] depotKey = steam3.DepotKeys[depotId]; var info = new DepotDownloadInfo(depotId, manifestId, installDir, contentName); info.depotKey = depotKey; return(info); }