Dedicated Windows Server (Steam) (WIP)

How to create a dedicated Server that correctly works with steam, and shows up listed by the Steam Master Server. Without requiring engine modifications! (4.25)

Updated almost 3 years ago Edit Page Revisions

In order to build dedicated servers for Windows, you need a source build of Unreal Engine. Check out Building Unreal Engine from Source. It's also not possible to build an engine from scratch with the blueprint-only project. You need to set up C++ project modules and compile your own engine.

For the sake of this guide, let's assume your game is simply called "MyGame"

Setting up the ServerTarget.cs

Setting up the MyGameServer.Targets.cs

using UnrealBuildTool;
using System.Collections.Generic;

[SupportedPlatforms(UnrealPlatformClass.Server)]
public class MyGameServerTarget : TargetRules
{
    public Site13ServerTarget(TargetInfo Target) : base(Target)
    {
        Type = TargetType.Server;
        DefaultBuildSettings = BuildSettingsVersion.V2;
        BuildEnvironment = TargetBuildEnvironment.Unique;
        ExtraModuleNames.Add("MyGame");
        
        // For dedicated server it is probably best that you always have logging, since they have no GUI.
        bUseLoggingInShipping = true; 

        // The name of your game as you set it on the Steamworks webpage.
        GlobalDefinitions.Add("UE4_PROJECT_STEAMPRODUCTNAME=\"MyGame\"");

        // This is what will appear under the "Game" tab in the Steam server browser. Steamworks list this under "Server browser name" in the Dedicated Servers section of your app.
        GlobalDefinitions.Add("UE4_PROJECT_STEAMGAMEDESC=\"MyGame\"");

        // I am not entirely sure what this is used for. Changing it seemed to not effect game searches.
        GlobalDefinitions.Add("UE4_PROJECT_STEAMGAMEDIR=\"MyGame\"");

        // The steam appID of your project.
        GlobalDefinitions.Add("UE4_PROJECT_STEAMSHIPPINGID=480");
    }
}

It's important that you use this syntax for the string \"Mygame\"". Simply writing "MyGame"will not work.

The defines such as UE4_PROJECT_STEAMPRODUCTNAMEdescribed above can be found in OnlineSessionAsyncServerSteam.cpp

Session Settings

There are numerous guides and tutorials online for creating a session. Since this page is specific for a Steam Dedicated Server I have only included the essential settings.

FOnlineSessionSettings SessionSettings;
SessionSettings.bIsDedicated = true;
SessionSettings.bIsLANMatch = false;       // If you want a lan match set this to true.
SessionSettings.bUsesPresence = false;    // Dedicated servers should always have this value set to false.
SessionSettings.bShouldAdvertise = true;
SessionSettings.BuildUniqueId = 1;        // Explained in greater detail further on.

// This sets what will appear in the Steam Server Browsers "Map" tab.
SessionSettings.Set(SETTING_MAPNAME, FString("TestMap"), EOnlineDataAdvertisementType::ViaOnlineServiceAndPing);

Build ID

Your UE4 build ID needs to match the settings set in Steamworks exactly.

The Build ID in Steamworks is set under the Dedicated Servers Tab for your app.

The "Latest version" field by default is set to 1.0.0.0. UE4 appears to use a simple integer for buildIDs so make sure you set this field to a regular number e.g "1".

Your SessionSettings.BuildUniqueID needs to match this number! Also, to ensure your packaged builds have the correct BuildID you can use the following setting in your DefaultEngine.ini file.

[OnlineSubsystem]
DefaultPlatformService=Steam
bUseBuildIdOVerride=true
BuildIdOverride=1

Port Forwarding / Firewall

In order for a Dedicated Server to be correctly listed by the Steam Master Server the following ports need to be opened and exceptions need to be set in the firewall.

  1. Port 7777 (TCP/UDP) (Used by UE4)

  2. Port 27015 (TCP/UDP) (Used by Steam)

The specifics of Port Forwarding depend on your router. Allowing communication through your Windows Firewall can be done by opening the "Windows Defender Firewall with Advanced Security" window. You will need to create four new "Inbound Rules", because one rule can only open either TCP or UDP so you will need two rules for 7777 and two rules for 27015 to open both TCP and UDP.

DefaultEngine.ini

[/Script/Engine.GameEngine]
+NetDriverDefinitions=(DefName="GameNetDriver",DriverClassName="OnlineSubsystemSteam.SteamNetDriver",DriverClassNameFallback="OnlineSubsystemUtils.IpNetDriver")

[OnlineSubsystem]
DefaultPlatformService=Steam
bUseBuildIdOVerride=true
BuildIdOverride=1

[OnlineSubsystemSteam]
bEnabled=true
SteamDevAppId=480

[/Script/OnlineSubsystemSteam.SteamNetDriver]
NetConnectionClassName="OnlineSubsystemSteam.SteamNetConnection"

Server Name

By default, UE4 uses the OwningUserID as the servers name. This is just a very long number, and not very descriptive.

While not the most convenient, the easiest way to set the server name is with a command argument. The argument is -SteamServerName=[YourServerName] . This can be set by creating a shortcut to your server .exe with which you start the server.

steam_appid.txt

Shipping builds will require a .txt file called steam_appid.txt containing your appID next to your server Binary.

All other build configurations do not require this steam_appid.txt file. They will create this file on server startup themselves and delete it once the server is shutdown.

Further Notes

  1. Many threads and guides online will claim that you need to manually copy certain steam.dll files into your binary folder. I have not found this to be the case in 4.25.

  2. When creating a Tool in steamworks you get the option to include common redistributables such as different versions of directX. On a regular AWS server instance the dedicated server will crash on startup because it is missing a DirectX runtime. Perhaps one of these runtimes is the correct one, I was too lazy to test them all, so in my case I downloaded the **"DirectX End-User Runtime Web Installer" **directly from microsofts webpage.