diff --git a/games/factorio_manager.sh b/games/factorio_manager.sh
index d96d9efb0d0aa092e064aab8dabb5367e740a2e5..8db4f717cd3dc70254250b1ea40d1f5eda2f1b94 100755
--- a/games/factorio_manager.sh
+++ b/games/factorio_manager.sh
@@ -824,6 +824,65 @@ function read_server_settings() {
     done
 }
 
+#
+# Validates paths according to internal tool rules or terminates the
+# program.
+#
+# This function helps to reduce boilerplate and centralise some common
+# checks around handling of various paths.
+#
+# Arguments:
+#
+#   $1 (path_test)
+#     Test to apply against the path. Supported tests are:
+#
+#       game_installations_directory
+#         Checks if path contains Factorio installations in
+#         sub-directories.
+#
+#       instance_directory_new
+#         Checks if path is unused and can be used for new instance.
+#
+#   $2 (path)
+#     Path that should be validated.
+#
+#   $3 (exit_code0
+#     Exit code to use when terminating the program.
+#
+# Exits:
+#
+#   If the path type is unsupported, or if the specified path does not
+#   conform to requirements for the specified path type.
+#
+function validate_path_or_terminate() {
+    local path_test="$1"
+    local path="$2"
+    local exit_code="$3"
+
+    if [[ $path_test == "game_installations_directory" ]]; then
+        # Make sure user has set directory with game installations -
+        # test both symlink and target destination.
+        if [[ ! -L $game_installations_directory || ! -d $game_installations_directory ]]; then
+            error "Game installations directory has not been properly set. Please run the set-game-dir command first."
+            exit "$exit_code"
+        fi
+
+    elif [[ $path_test == "instance_directory_new" ]]; then
+        if [[ -e $path/config.ini ]]; then
+            error "Instance already exists."
+            exit "$exit_code"
+        fi
+
+        if [[ -e $path ]]; then
+            error "Instance directory already exists, but does not contain a valid Factorio instance: $path."
+            exit "$exit_code"
+        fi
+    else
+        error "Unable to validate path '$path', unsupported test requested: '$path_test'."
+        exit "$ERROR_GENERAL"
+    fi
+}
+
 # Define error codes.
 SUCCESS=0
 ERROR_ARGUMENTS=1
@@ -918,17 +977,7 @@ if [[ $command == set-game-dir ]]; then
 #==========#
 elif [[ $command == versions ]]; then
 
-    # Make sure user has set directory with game installations - test
-    # both symlink and target destination.
-    if [[ ! -L $game_installations_directory ]]; then
-        error "Game installations directory has not been properly set. Please run the set-game-dir command first."
-        exit "$ERROR_CONFIGURATION"
-    fi
-
-    if [[ ! -d $game_installations_directory ]]; then
-        error "Game installations directory has not been properly set. Please run the set-game-dir command first."
-        exit "$ERROR_CONFIGURATION"
-    fi
+    validate_path_or_terminate "game_installations_directory" "$game_installations_directory" "$ERROR_CONFIGURATION"
 
     echo "Locally available Factorio versions:"
     echo
@@ -961,17 +1010,7 @@ elif [[ $command == list ]]; then
 # create #
 #========#
 elif [[ $command == create ]]; then
-    # Make sure user has set directory with game installations - test
-    # both symlink and target destination.
-    if [[ ! -L $game_installations_directory ]]; then
-        error "Game installations directory has not been properly set. Please run the set-game-dir command first."
-        exit "$ERROR_CONFIGURATION"
-    fi
-
-    if [[ ! -d $game_installations_directory ]]; then
-        error "Game installations directory has not been properly set. Please run the set-game-dir command first."
-        exit "$ERROR_CONFIGURATION"
-    fi
+    validate_path_or_terminate "game_installations_directory" "$game_installations_directory" "$ERROR_CONFIGURATION"
 
     # Read positional arguments.
     instance="${1-}"
@@ -988,10 +1027,7 @@ elif [[ $command == create ]]; then
         exit "$ERROR_ARGUMENTS"
     fi
 
-    if [[ -e $instance_directory ]]; then
-        error "Instance already exists."
-        exit "$ERROR_ARGUMENTS"
-    fi
+    validate_path_or_terminate "instance_directory_new" "$instance_directory" "$ERROR_ARGUMENTS"
 
     # Display list of available Factorio versions and let user pick one.
     echo "The following versions of Factorio are locally available:"
@@ -1896,10 +1932,7 @@ elif [[ $command == copy ]]; then
         exit "$ERROR_GENERAL"
     fi
 
-    if [[ -e $destination_instance_directory ]]; then
-        error "Instance already exists."
-        exit "$ERROR_ARGUMENTS"
-    fi
+    validate_path_or_terminate "instance_directory_new" "$destination_instance_directory" "$ERROR_ARGUMENTS"
 
     (
         # Obtain lock - Factorio uses the same mechanism, so we should
@@ -2046,11 +2079,7 @@ elif [[ $command == import ]]; then
     import_entries["player-data.json"]="contains global information about the player, such as username, login token, chat history, etc."
     import_entries["saves"]="contains savegames"
 
-    # Ensure we are working with valid directories.
-    if [[ -e $instance_directory ]]; then
-        error "Instance already exists."
-        exit "$ERROR_ARGUMENTS"
-    fi
+    validate_path_or_terminate "instance_directory_new" "$instance_directory" "$ERROR_ARGUMENTS"
 
     if [[ ! -f $source_directory/bin/x64/factorio ]]; then
         error "Could not locate Factorio binary in source directory under: $source_directory/bin/x64/factorio"
@@ -2186,10 +2215,7 @@ elif [[ $command == create-server ]]; then
         exit "$ERROR_ARGUMENTS"
     fi
 
-    if [[ -e $instance_directory ]]; then
-        error "Instance already exists."
-        exit "$ERROR_ARGUMENTS"
-    fi
+    validate_path_or_terminate "instance_directory_new" "$instance_directory" "$ERROR_ARGUMENTS"
 
     # Display list of available Factorio versions and let user pick one.
     echo "The following versions of Factorio are locally available:"