You've already forked UnrealEngineUWP
mirror of
https://github.com/izzy2lost/UnrealEngineUWP.git
synced 2026-03-26 18:15:20 -07:00
#lockdown Nick.Penwarden Change 3315047 on 2017/02/21 by Mieszko.Zielinski@mieszko.zielinski_T4675_Orion HTN code first check in #UE4 #rb none #test currently unused Change 3314042 on 2017/02/21 by Jason.Bestimt@Jason.Bestimt_Dev-General #ORION_DG - DAILY Main @ CL 3313484 #RB:none #Tests:none Change 3313355 on 2017/02/20 by Uriel.Doyon@uriel.doyon_PC2_Orion Changed the preliminary GPU benchmark workloads to take into account the target workload. This is to prevent running the last test with poor performance, risking a driver reset. #jira OR-29915 #rb marcus.wassmer #test Run the game triggering benchmarks Change 3312553 on 2017/02/20 by Mieszko.Zielinski@mieszko.zielinski_T4675_Orion Implemented a simple AITask for running EQS queries #UE4 #rb Lukasz.Furman #test golden path Change 3311661 on 2017/02/20 by Jason.Bestimt@Jason.Bestimt_Dev-General #ORION_DG - Merge MAIN @ CL 3311631 #RB:none #Tests:none Change 3310392 on 2017/02/17 by Daniel.Lamb@daniel.lamb_T3905_6612 Unreal pak now outputs to named log files instead of timestamps. #rb Trivial #test Cook deploy paragon #jira OR-36057 Change 3310196 on 2017/02/17 by Clayton.Langford@RDU-WD-8359_3635_Paragon_DevGen Created an event to be fired whenever a GameplayCue is routed that passes all relevant info about that GC. Added a listener in OrionPhasedFunctionalTest that parses that event into a string and stores it in an array to be accessed from a test phase later. #test PIE #rb Ben.Salem, Adric.Worley Change 3308437 on 2017/02/16 by Jason.Bestimt@Jason.Bestimt_Dev-General #ORION_DG - Merge MAIN @ CL 3308413 (Prep for Merge up) #RB:none #Tests:none Change 3306497 on 2017/02/16 by Andrew.Grant@andrew.grant.T6730.orion.floating Fix for compilation issue with USE_MALLOC_STOMP #rb none #tests compiled with malloc_stomp Change 3306468 on 2017/02/16 by Cody.Haskell@OrionStream #Orion - Text popup work for Shield. If you click on an OrionEditableTextBox while running the game with -gfn, a special popup is called. Should do nothing normally. #rb none #tests PIE, golden path. Change 3305945 on 2017/02/16 by David.Ratti@David.Ratti_G6218_Orion.Dev-General Remove unused/deprecated UGameplayEffectExtension class #rb #tests none Change 3304630 on 2017/02/15 by Jason.Bestimt@Jason.Bestimt_Dev-General #ORION_DG - Merge Mieszko stuff from MAIN to DG #RB:none #TestS:none #!codereview: mieszko.zielinski Change 3303785 on 2017/02/15 by jason.bestimt@Jason.Bestimt_Dev-General #ORION_MAIN - Merge 38.3 @ CL 3303224 #RB:none #Tests:none #!ROBOMERGE-SOURCE: CL 3303718 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) #!ROBOMERGE-SAYS: Unresolved conflicts. jason.bestimt, please merge this change by hand. //Orion/Dev-General/OrionGame/Content/UI/DeckBuilder/DeckBuilderRoot.uasset - can't integrate exclusive file already opened //Orion/Dev-General/OrionGame/Content/UI/Master_Layouts/FrontEnd.uasset - can't integrate exclusive file already opened #!codereview: jason.bestimt Change 3302382 on 2017/02/14 by Alexis.Matte@amatte-orion-dev-general Fix import of morph target when there is no animation #jira UE-41383 #jira OR-35859 #rb none #test none Change 3301538 on 2017/02/14 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: jason.bestimt #ORION_MAIN - Merge 38.3 @ CL 3301392 #RB:none #Tests:none #!ROBOMERGE-SOURCE: CL 3301481 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3299985 on 2017/02/13 by Lukasz.Furman@Lukasz.Furman_T7320_OrionStream added time limit to "get out of overlap" move for minons to avoid getting stuck in moving to inaccessbile spots #jira OR-35834 #rb Mieszko.Zielinski #tests PIE Change 3299732 on 2017/02/13 by Mieszko.Zielinski@mieszko.zielinski_T4675_Orion Tweaked the way EQS tests of negative score get normalized #UE4 #rb none #test golden path + math #!codereview Lukasz.Furman, John.Abercrombie Change 3299724 on 2017/02/13 by Mieszko.Zielinski@mieszko.zielinski_T4675_Orion Generic AI interface extensions #UE4 Mostly getters #rb none #test golden path Change 3299717 on 2017/02/13 by Mieszko.Zielinski@mieszko.zielinski_T4675_Orion A little tweak to VisLog's point labels drawing - if there's only one point in a set it will no longer append '_0' to the label #UE4 #rb none #test PIE Change 3299527 on 2017/02/13 by Paul.Moore@OrionWorkspace_Dev-General #orion #mms - Update libWebSockets binaries to fix Linux server web socket connections. #tests matchmaking, mms #rb none Change 3299278 on 2017/02/13 by David.Ratti@David.Ratti_G6218_Orion.Dev-General Ability Task Pass: tasks should not broadcast out (back into ability graph) if the owning ability has completed EndAbility. #rb none #tests pie, golden path Change3297884on 2017/02/10 by Paul.Moore@OrionWorkspace_Dev-General #mms - Enable SSL module for PS4 (needed by OpenSSL when using WebSockets). - Turn on verbose logging for WebSockets module for initial MMS debugging. #tests PS4 #rb none Change 3296911 on 2017/02/10 by John.Pollard@John.Pollard_T2802_Orion_DevGeneral Encode user search string so we support special characters #rb RyanG #tests Replays Change 3296746 on 2017/02/10 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: jason.bestimt #ORION_MAIN - Merge 38.3 @ CL 3296659 #RB:none #Tests:none #!ROBOMERGE-SOURCE: CL 3296735 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3296705 on 2017/02/10 by Daniel.Lamb@daniel.lamb_T3905_6612 Added support to the cooker for iterating shared builds. #rb Not used yet #test Fast cook paragon Change 3295747 on 2017/02/09 by Paul.Moore@OrionWorkspace_Dev-General #orion #mms - Integrated WS upgrade header functionality with latest Fortnite libws changes. - Added "ws" and "wss" protocols to web socket manager context. #rb rob.cannaday #!codereview rob.cannaday, james.hopkin #tests win64, ps4 Change 3295579 on 2017/02/09 by John.Pollard@John.Pollard_T2802_Orion_DevGeneral Fix for replay backward compatibility from John.Pollard #tests #rb na Merging using OrionScratchReleaseMapping Change 3295506 on 2017/02/09 by Rolando.Caloca@rolando.caloca_T3903_OrionMainS O - Added option for force recompute tangents using skin cache #rb none #jira UE-41541 #tests Editor run, toggle, restart Change 3295461 on 2017/02/09 by Lukasz.Furman@Lukasz.Furman_T7320_OrionStream fixed huge interpolation times for linear network smoothing on stationary characters, fixed mismatch in movement Base between NavWalking server and Walking client, causing some stationary characters to float in midair copy of CL# 3295439 #jira OR-35664, OR-35572 #rb none #tests game Change 3294954 on 2017/02/09 by Paul.Moore@OrionWorkspace_Dev-General #orion #mms - Integrating Fortnite WebSocket changes into Orion that fixes some win10 issues. #!codereview rob.cannaday, james.hopkin #tests compile ps4, linux, win64 #rb none Change 3294947 on 2017/02/09 by Daniel.Lamb@daniel.lamb_T3905_6612 The generate stub return result is considered as success when saving cooked packages. Fixes bug with cooking blueprint nativized packages. #rb Trivial #test Cook paragon Change 3293307 on 2017/02/08 by Andrew.Grant@andrew.grant.T6730.orion.floating Fix for issue in last checkin - need to clear activecontext regardless #rb none #tests solo smoke with nullrhi Change 3293284 on 2017/02/08 by Ryan.Gerleve@Ryan.Gerleve_T3703_Orion Allow setting the per-frame time limit for processing queued bunches separately for instant replays, since they may have more strict timing/framerate requirements. #rb john.pollard #tests golden path Change 3293148 on 2017/02/08 by Andrew.Grant@andrew.grant.T6730.orion.floating Fixed invalid memory access* with nullrhi and suppressed IME warning if no valid window handle exists (*Likely only an issue when running with memory validation) #rb none #tests verified invalid access exception no longer occurs with nullrhi #!review-3293149 @Matt.Khulenschmidt Change 3293103 on 2017/02/08 by Max.Chen@Max.Chen_T4664_Orion_Main Sequencer: Fix build #jira OR-34918 #rb none #tests none Change 3292921 on 2017/02/08 by Max.Chen@Max.Chen_T4664_Orion_Main Sequencer: Force local player to maintain x fov axis. #jira OR-34918 #rb david.ratti #tests Render/PIE a level sequence and test that the camera isn't zoomed in. Change 3292869 on 2017/02/08 by David.Ratti@David.Ratti_G6218_Orion.Dev-General Yet more logging for OR-35448 #rb #tests none Change 3292821 on 2017/02/08 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: rob.cannaday PS4 libwebsockets build fix Update build cs files to point to PS4 file location Copy libwebsocket include directory from Fortnite to Orion #rb paul.moore #tests compile/link Win64 Development Editor, PS4 Debug, Linux Development Server #!ROBOMERGE-SOURCE: CL 3292820 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3292277 on 2017/02/08 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: jason.bestimt #ORION_MAIN - Merge DMM @ CL 3292219 #RB:none #Tests:none [CODEREVIEW] paul.moore, benjamin.crocker #QAReview #!ROBOMERGE-SOURCE: CL 3292276 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3292211 on 2017/02/08 by Andrew.Grant@andrew.grant.T6730.orion.floating Pulling new ags library from Release-4.15 and reverting hack that disabled feature for AMD users #rb Marcus.Wassmer #tests compiled Change 3292167 on 2017/02/08 by David.Ratti@David.Ratti_G6218_Orion.Dev-General Additional logging for OR-35448 #rb none #tests pie Change 3289462 on 2017/02/06 by Ben.Salem@ben.salem_OrionMain Adding priority filters to Automation tests, also commands to filter on priority levels. #rb adric worley #tests Compiled, ran a few commands to verify it works. Change3288801on 2017/02/06 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: jason.bestimt #ORION_MAIN - Merge 37.2 (38.3) @ CL3288681#RB:none #Tests:none #!ROBOMERGE-SOURCE: CL 3288800 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3288750 on 2017/02/06 by Daniel.Lamb@daniel.lamb_T3905_6612 Fixed issue when cooking client and server platforms in single cook some packages would be marked incorrectly because they would be stripped when from client / server. #rb Andrew.Grant #test Cook paragon Change 3288624 on 2017/02/06 by Andrew.Grant@andrew.grant.T6730.orion.floating Unlocked network version #rb #tests na OR-35603 Change 3288612 on 2017/02/06 by Daniel.Lamb@daniel.lamb_T3905_6612 Added more ini settings to the iterative ini blacklist. #rb Trivial #test Iterative Cook Paragon Change 3288184 on 2017/02/06 by Andrew.Grant@andrew.grant.T6730.orion.floating Downgraded warning to display #!review-3288185 @David.Ratti #rb none #tests none Change 3287634 on 2017/02/06 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: jason.bestimt #ORION_MAIN - Merge 37.2 @ 3287498 #RB:none #Tests:none #!ROBOMERGE-SOURCE: CL 3287619 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3286668 on 2017/02/03 by Alexis.Matte@amatte-orion-dev-general Fix a crash when importing a LOD containing different material with less sections #rb none #test none Change 3286112 on 2017/02/03 by Alexis.Matte@amatte-orion-dev-general Fix the re-import skeletal mesh regression, where all material disapear. #jira UE-41294 #rb matt.kuhlenschmidt #test see the jira Change3285859on 2017/02/03 by Daniel.Lamb@daniel.lamb_T3905_6612 Fixed merge error from last checkin with the DDC commandlet #!codereview Matthew.Griffin #test DDC commandlet paragon #rb None Change 3285637 on 2017/02/03 by Ryan.Gerleve@Ryan.Gerleve_T3703_Orion Pass in the DemoNetDriver pointer to the ConcurrentWithSlateTickTask instead of accessing it from the world in the task itself. #rb john.pollard #tests golden path Change 3285479 on 2017/02/03 by Mieszko.Zielinski@mieszko.zielinski_T4675_Orion Made bot communicate ults when they're up, not when they're using it #Orion CL also contains a bit of code shuffling around, preparing ground for HTN plug in #rb none #test golden path Change 3285125 on 2017/02/03 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: jason.bestimt #ORION_MAIN - Merge 37.2 @ CL 3285078 #RB:none #Tests:none #!ROBOMERGE-SOURCE: CL 3285124 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3283996 on 2017/02/02 by Michael.Trepka@Michael.Trepka_PC_Orion-Dev-General Added UGameUserSettings::GetRecommandedResolutionScale() to replace UOrionGameUserSettings::GetDefaultResolutionScale(). This makes things less confusing (UGameUserSettings::GetRecommandedResolutionScale() returns scale recommended based on results of the benchmark and UGameUserSettings::GetDefaultResolutionScale() returns scale based on user settings) and fixes a regression introduced in 3257936 (OR-35544) #rb Cody.Haskell #tests Tested on PC Change 3283951 on 2017/02/02 by Daniel.Lamb@daniel.lamb_T3905_6612 Ensure DDC commandlet calls begincacheforcookedplatformdata correctly. #rb None #!codereview Matthew.Griffin #test DDC commandlet paragon. Change 3283874 on 2017/02/02 by Lina.Halper@Lina.Halper_Orion fix for invalid resource issue #rb: none #code review: Daniel.Wright #tests: compile and editor with wolf Change 3283621 on 2017/02/02 by Laurent.Delayen@laurent.delayen_Work2016_Orion Femme WIP whip aiming for Q ability. #rb none #tests Femme Change 3283216 on 2017/02/02 by jason.bestimt@Jason.Bestimt_Dev-General #ORION_MAIN - Merge 37.2 @ CL3282900#RB:none #Tests:none #!ROBOMERGE-SOURCE: CL 3283199 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3282954 on 2017/02/02 by Lina.Halper@Lina.Halper_Orion It becomes invalid on the resource, so checking null, but still wip on verifying this with Daniel Wright. He's sick out. #rb:none #tests: compile #code review:Daniel.Wright #Jira: OR-35418 Change 3281993 on 2017/02/01 by Daniel.Lamb@daniel.lamb_T3905_6612 Removed default unattended flag. #rb Trivial #test PS4 cook run paragon. Change 3281990 on 2017/02/01 by Daniel.Lamb@daniel.lamb_T3905_6612 Potential fix for deterministic cooking issue with UMovieSceneSignedObjects. #rb Andrew.Grant #!codereview Max.Preussner #test Cook and run paragon ps4. Change 3281610 on 2017/02/01 by Laurent.Delayen@laurent.delayen_Work2016_Orion AimOffsetLookAt is now thread safe. #rb lina.halper #tests femme Change 3281609 on 2017/02/01 by Laurent.Delayen@laurent.delayen_Work2016_Orion Fixed 'Convert to AimOffset LookAt' option being broken in Persona. #rb lina.halper #tests works for Femme now. Change 3281019 on 2017/02/01 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: jason.bestimt #ORION_MAIN - Merge 37.2 @ CL 3280498 #RB:none #Tests:none #!ROBOMERGE-SOURCE: CL 3281018 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3280813 on 2017/02/01 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: matthew.griffin Prevent inclusion of NotForLicensees files when staging CrashReportClient config files #rb none #tests none #!ROBOMERGE-SOURCE: CL 3280812 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3279921 on 2017/01/31 by Yanni.Tripolitis@yanni.tripolitis_Dev_General_Cary Fixed an error in the Round MF, that was somehow "leaked" into Paragon from Odin. #lockdown Billy.Rivers, Adam.Bellefeuil #!codereview Tim.Elek Change 3279178 on 2017/01/31 by Daniel.Lamb@daniel.lamb_T3905_6612 Fixed up diff files commandlet stack information #rb Joe.Conley #test Diff cooked packages Change 3279084 on 2017/01/31 by Andrew.Grant@andrew.grant.T6730.orion.floating Merging //UE4/Main at 3276432 through Orion-Staging #rb #tests na Change 3279078 on 2017/01/31 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: jason.bestimt #ORION_MAIN - Merge 37.2 @ CL 3279032 #RB:none #Tests:none #!ROBOMERGE-SOURCE: CL3279077in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3277908 on 2017/01/30 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: jason.bestimt #ORION_37 - Fix for "-game" crash with missing meta data #RB:none #Tests:none [CodeReviewed]: andrew.grant, jamie.dale, mieszko.zielinski #!ROBOMERGE-SOURCE: CL 3277901 in //Orion/Release-37/... via CL 3277902 via CL 3277904 via CL 3277905 #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3277520 on 2017/01/30 by Andrew.Grant@andrew.grant.T6730.orion.floating Workaround for OR-35418 #!ROBOMERGE: Main #rb none #tests verified ShortSoloGame test completes without a crash Change 3277357 on 2017/01/30 by Daniel.Lamb@daniel.lamb_T3905_6612 Fixed the rebuild lighting commandlet. #rb Trivial #test Rebuild lighting dev general Change 3277322 on 2017/01/30 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: jason.bestimt #ORION_MAIN - Merge 37.2 @ CL 3277275 #RB:none #Tests:none #!ROBOMERGE-SOURCE: CL 3277296 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3277210 on 2017/01/30 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: andrew.grant Non-shipping test changes: Fixed issue where with -stdout messages would be duplicated due to FeedbackContextAnsi echoing to stdout by default Changed stdout output to postfix instead of trail newlines Firstpass of finding and displaying crash callstacks in Orion Test Framework. #rb none #tests ran test framework with tests that purposefully crashed/checked #!ROBOMERGE-SOURCE: CL 3276889 in //Orion/Release-37/... via CL 3277207 via CL 3277208 via CL 3277209 #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3276774 on 2017/01/29 by Andrew.Grant@andrew.grant.T6730.orion.floating Fix for non-unity issue. #tests compiled #rb none #!ROBOMERGE: Main, DUI Change 3276594 on 2017/01/28 by Lina.Halper@Lina.Halper_Orion Checked in potential fix for nonunity build issue #rb:none #tests:compile Change 3275806 on 2017/01/27 by Ben.Salem@ben.salem_OrionMain Adding in a checkpointing system for automated test passes where, if a client crashes while running a pass, on reboot and reissue of the automation command the test pass will start off where it left off, skipping the crashing test. #rb clayton.langford #tests Ran several dozen test passses. Seriously. #!codereview steve.white, bob.ferreira, clayton.langford, adric.worley Change 3275803 on 2017/01/27 by Shaun.Kime@shaun.kime_RDU-WD-9788_oriondevgen Paragon has retainer widgets with no World set. When encountered, they can cause the scene list to be desynchronized with the rendering thread. This logic resolves the issue by registering a null scene in this case, properly setting the slate scene index for subsequent slate draw calls. #rb nick.darnell #jira OR-34919 #TESTS na Change 3275533 on 2017/01/27 by Max.Chen@Max.Chen_T4664_Orion_Main Sequencer: Switch to static pointer to fix crash when tearing down curve editor. #jira UE-40796 #rb andrew.rodham #tests none Change 3275093 on 2017/01/27 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: jason.bestimt #ORION_MAIN - Merge 37.2 @ CL 3273298 #RB:none #Tests:none #!ROBOMERGE-SOURCE: CL 3273417 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3274700 on 2017/01/26 by Lina.Halper@Lina.Halper_Orion #Anim curve crash on cooking - fixed crash during cooking while accessing default value of material - this code doesn't have to run during cooking with inactive world, so I'm checking that #code review: Daniel.Wright, Chris.Bunner, Jurre.DeBaare #rb: none #tests: cooking Change 3274129 on 2017/01/26 by Lina.Halper@Lina.Halper_Orion Fixed safer to get featurelevel #rb: Daniel.Wright #tests: compile/wolf Change 3274012 on 2017/01/26 by Lukasz.Furman@Lukasz.Furman_T7320_OrionStream fixed crash in navigation grids #jira OR-35356 #rb none #tests PIE Change 3273803 on 2017/01/26 by Lina.Halper@Lina.Halper_Orion Fixed issue with animation curve getting reset to 0.f - the issue is that skeleton contains material flag types, so now it just keeps setting the value - even after I fix validation check, it still cleared it due to the material curve not found anymore, so added to support default value setting #jira: OR-34563 #rb: Martin.Wilson, Chris.Bunner, Benn.Gallagher #code review: Martin.Wilson, Daniel.Wright #tests: wolf, coil Change3273257on 2017/01/26 by Alexis.Matte@amatte-orion-dev-general Isolate by material slot instead of section index. Add UI to isolate and highlight material in the material panel #rb matt.kuhlenschmidt #jira UE-41131 #tests none Change 3272527 on 2017/01/25 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: chris.bunner Ensure FSceneRenderTargets snapshot copies default clear colors. #tests Golden path on lowest and high settings #rb None #lockdown Jason.Bestimt #jira OR-34905 #!ROBOMERGE-SOURCE: CL 3272507 in //Orion/Release-37.1/... via CL 3272521 via CL 3272525 #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3272244 on 2017/01/25 by Rolando.Caloca@rolando.caloca_T3903_OrionMainS Show more info when a material instance failed to compile #jira OR-34626 #tests Forced crash in the debugger #rb Daniel.Wright Change 3272109 on 2017/01/25 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: philip.buuck Fix bad merge from Main #rb Dan.Hertzka #tests PIE [CodeReviewed] Andrew.Grant #lockdown Andrew.Grant #!ROBOMERGE-SOURCE: CL 3272106 in //Orion/Release-37.1/... via CL 3272107 via CL 3272108 #!ROBOMERGE-BOT: ORION (Main -> Dev-General) Change 3271721 on 2017/01/25 by Lukasz.Furman@Lukasz.Furman_T7320_OrionStream jungle minions will spawn navigation obstacles when they are stuck in static geometry, fixed issues with falling off cliffs #jira OR-35054 #rb Mieszko.Zielinski #tests PIE Change 3271432 on 2017/01/25 by Jason.Bestimt@ROBOMERGE_ORION_Dev_General #!ROBOMERGE-AUTHOR: jason.bestimt #ORION_MAIN - Merge 37.2 @ CL 3271043 #RB:none #Tests:none #!ROBOMERGE-SOURCE: CL 3271429 in //Orion/Main/... #!ROBOMERGE-BOT: ORION (Main -> Dev-General) [CL 3322856 by Andrew Grant in Main branch]
1096 lines
34 KiB
C#
1096 lines
34 KiB
C#
// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved.
|
|
using System;
|
|
using System.Collections.Generic;
|
|
using System.IO;
|
|
using System.Text.RegularExpressions;
|
|
using System.Threading;
|
|
using System.Reflection;
|
|
using System.Linq;
|
|
using System.Net.NetworkInformation;
|
|
using System.Collections;
|
|
using AutomationTool;
|
|
using UnrealBuildTool;
|
|
|
|
/// <summary>
|
|
/// Helper command to run a game.
|
|
/// </summary>
|
|
/// <remarks>
|
|
/// Uses the following command line params:
|
|
/// -cooked
|
|
/// -cookonthefly
|
|
/// -dedicatedserver
|
|
/// -win32
|
|
/// -noclient
|
|
/// -logwindow
|
|
/// </remarks>
|
|
public partial class Project : CommandUtils
|
|
{
|
|
#region Fields
|
|
|
|
/// <summary>
|
|
/// Thread used to read client log file.
|
|
/// </summary>
|
|
private static Thread ClientLogReaderThread = null;
|
|
|
|
/// <summary>
|
|
/// Process for the server, can be set by the cook command when a cook on the fly server is used
|
|
/// </summary>
|
|
public static IProcessResult ServerProcess;
|
|
|
|
#endregion
|
|
|
|
#region Run Command
|
|
|
|
// debug commands for the engine to crash
|
|
public static string[] CrashCommands =
|
|
{
|
|
"crash",
|
|
"CHECK",
|
|
"GPF",
|
|
"ASSERT",
|
|
"ENSURE",
|
|
"RENDERCRASH",
|
|
"RENDERCHECK",
|
|
"RENDERGPF",
|
|
"THREADCRASH",
|
|
"THREADCHECK",
|
|
"THREADGPF",
|
|
};
|
|
|
|
/// <summary>
|
|
/// For not-installed runs, returns a temp log folder to make sure it doesn't fall into sandbox paths
|
|
/// </summary>
|
|
/// <returns></returns>
|
|
private static string GetLogFolderOutsideOfSandbox()
|
|
{
|
|
return GlobalCommandLine.Installed ?
|
|
CmdEnv.LogFolder :
|
|
CombinePaths(Path.GetTempPath(), CommandUtils.EscapePath(CmdEnv.LocalRoot), "Logs");
|
|
}
|
|
|
|
/// <summary>
|
|
/// Fot not-installed runs, copies all logs from the temp log folder back to the UAT log folder.
|
|
/// </summary>
|
|
private static void CopyLogsBackToLogFolder()
|
|
{
|
|
if (!GlobalCommandLine.Installed)
|
|
{
|
|
var LogFolderOutsideOfSandbox = GetLogFolderOutsideOfSandbox();
|
|
var TempLogFiles = FindFiles_NoExceptions("*", false, LogFolderOutsideOfSandbox);
|
|
foreach (var LogFilename in TempLogFiles)
|
|
{
|
|
var DestFilename = CombinePaths(CmdEnv.LogFolder, Path.GetFileName(LogFilename));
|
|
CopyFile_NoExceptions(LogFilename, DestFilename);
|
|
}
|
|
}
|
|
}
|
|
|
|
public static void Run(ProjectParams Params)
|
|
{
|
|
Params.ValidateAndLog();
|
|
if (!Params.Run)
|
|
{
|
|
return;
|
|
}
|
|
|
|
Log("********** RUN COMMAND STARTED **********");
|
|
|
|
var LogFolderOutsideOfSandbox = GetLogFolderOutsideOfSandbox();
|
|
if (!GlobalCommandLine.Installed && ServerProcess == null)
|
|
{
|
|
// In the installed runs, this is the same folder as CmdEnv.LogFolder so delete only in not-installed
|
|
DeleteDirectory(LogFolderOutsideOfSandbox);
|
|
CreateDirectory(LogFolderOutsideOfSandbox);
|
|
}
|
|
var ServerLogFile = CombinePaths(LogFolderOutsideOfSandbox, "Server.log");
|
|
var ClientLogFile = CombinePaths(LogFolderOutsideOfSandbox, Params.EditorTest ? "Editor.log" : "Client.log");
|
|
|
|
try
|
|
{
|
|
RunInternal(Params, ServerLogFile, ClientLogFile);
|
|
}
|
|
catch
|
|
{
|
|
throw;
|
|
}
|
|
finally
|
|
{
|
|
CopyLogsBackToLogFolder();
|
|
}
|
|
|
|
Log("********** RUN COMMAND COMPLETED **********");
|
|
}
|
|
|
|
private static void RunInternal(ProjectParams Params, string ServerLogFile, string ClientLogFile)
|
|
{
|
|
// Setup server process if required.
|
|
if (Params.DedicatedServer && !Params.SkipServer)
|
|
{
|
|
if (Params.ServerTargetPlatforms.Count > 0)
|
|
{
|
|
TargetPlatformDescriptor ServerPlatformDesc = Params.ServerTargetPlatforms[0];
|
|
ServerProcess = RunDedicatedServer(Params, ServerLogFile, Params.RunCommandline);
|
|
// With dedicated server, the client connects to local host to load a map.
|
|
if (ServerPlatformDesc.Type == UnrealTargetPlatform.Linux)
|
|
{
|
|
Params.MapToRun = Params.ServerDeviceAddress;
|
|
}
|
|
else
|
|
{
|
|
Params.MapToRun = "127.0.0.1";
|
|
}
|
|
}
|
|
else
|
|
{
|
|
throw new AutomationException("Failed to run, server target platform not specified");
|
|
}
|
|
}
|
|
else if (Params.FileServer && !Params.SkipServer)
|
|
{
|
|
ServerProcess = RunFileServer(Params, ServerLogFile, Params.RunCommandline);
|
|
}
|
|
|
|
if (ServerProcess != null)
|
|
{
|
|
Log("Waiting a few seconds for the server to start...");
|
|
Thread.Sleep(5000);
|
|
}
|
|
|
|
if (!Params.NoClient)
|
|
{
|
|
Log("Starting Client....");
|
|
|
|
var SC = CreateDeploymentContext(Params, false);
|
|
|
|
ERunOptions ClientRunFlags;
|
|
string ClientApp;
|
|
string ClientCmdLine;
|
|
SetupClientParams(SC, Params, ClientLogFile, out ClientRunFlags, out ClientApp, out ClientCmdLine);
|
|
|
|
// Run the client.
|
|
if (ServerProcess != null)
|
|
{
|
|
RunClientWithServer(SC, ServerLogFile, ServerProcess, ClientApp, ClientCmdLine, ClientRunFlags, ClientLogFile, Params);
|
|
}
|
|
else
|
|
{
|
|
RunStandaloneClient(SC, ClientLogFile, ClientRunFlags, ClientApp, ClientCmdLine, Params);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Client
|
|
|
|
private static void RunStandaloneClient(List<DeploymentContext> DeployContextList, string ClientLogFile, ERunOptions ClientRunFlags, string ClientApp, string ClientCmdLine, ProjectParams Params)
|
|
{
|
|
if (Params.Unattended)
|
|
{
|
|
string LookFor = "Bringing up level for play took";
|
|
bool bCommandlet = false;
|
|
|
|
if (Params.RunAutomationTest != "")
|
|
{
|
|
LookFor = "Automation Test Succeeded";
|
|
}
|
|
else if (Params.RunAutomationTests)
|
|
{
|
|
LookFor = "Automation Test Queue Empty";
|
|
}
|
|
else if (Params.EditorTest)
|
|
{
|
|
LookFor = "Asset discovery search completed in";
|
|
}
|
|
// If running a commandlet, just detect a normal exit
|
|
else if (ClientCmdLine.IndexOf("-run=", StringComparison.InvariantCultureIgnoreCase) >= 0)
|
|
{
|
|
LookFor = "Game engine shut down";
|
|
bCommandlet = true;
|
|
}
|
|
|
|
{
|
|
|
|
string AllClientOutput = "";
|
|
int LastAutoFailIndex = -1;
|
|
IProcessResult ClientProcess = null;
|
|
FileStream ClientProcessLog = null;
|
|
StreamReader ClientLogReader = null;
|
|
Log("Starting Client for unattended test....");
|
|
ClientProcess = Run(ClientApp, ClientCmdLine + " -testexit=\"" + LookFor + "\"", null, ClientRunFlags | ERunOptions.NoWaitForExit);
|
|
while (!FileExists(ClientLogFile) && !ClientProcess.HasExited)
|
|
{
|
|
Log("Waiting for client logging process to start...{0}", ClientLogFile);
|
|
Thread.Sleep(2000);
|
|
}
|
|
if (FileExists(ClientLogFile))
|
|
{
|
|
Thread.Sleep(2000);
|
|
Log("Client logging process started...{0}", ClientLogFile);
|
|
ClientProcessLog = File.Open(ClientLogFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
|
|
ClientLogReader = new StreamReader(ClientProcessLog);
|
|
}
|
|
if (ClientLogReader == null)
|
|
{
|
|
throw new AutomationException("Client exited without creating a log file.");
|
|
}
|
|
bool bKeepReading = true;
|
|
bool WelcomedCorrectly = false;
|
|
bool bClientExited = false;
|
|
DateTime ExitTime = DateTime.UtcNow;
|
|
|
|
while (bKeepReading)
|
|
{
|
|
if (!bClientExited && ClientProcess.HasExited)
|
|
{
|
|
ExitTime = DateTime.UtcNow;
|
|
bClientExited = true;
|
|
}
|
|
string ClientOutput = ClientLogReader.ReadToEnd();
|
|
if (!String.IsNullOrEmpty(ClientOutput))
|
|
{
|
|
if (bClientExited)
|
|
{
|
|
ExitTime = DateTime.UtcNow; // as long as it is spewing, we reset the timer
|
|
}
|
|
AllClientOutput += ClientOutput;
|
|
Console.Write(ClientOutput);
|
|
|
|
if (AllClientOutput.LastIndexOf(LookFor) > AllClientOutput.IndexOf(LookFor))
|
|
{
|
|
WelcomedCorrectly = true;
|
|
Log("Test complete...");
|
|
bKeepReading = false;
|
|
}
|
|
else if (Params.RunAutomationTests)
|
|
{
|
|
int FailIndex = AllClientOutput.LastIndexOf("Automation Test Failed");
|
|
int ParenIndex = AllClientOutput.LastIndexOf(")");
|
|
if (FailIndex >= 0 && ParenIndex > FailIndex && FailIndex > LastAutoFailIndex)
|
|
{
|
|
string Tail = AllClientOutput.Substring(FailIndex);
|
|
int CloseParenIndex = Tail.IndexOf(")");
|
|
int OpenParenIndex = Tail.IndexOf("(");
|
|
string Test = "";
|
|
if (OpenParenIndex >= 0 && CloseParenIndex > OpenParenIndex)
|
|
{
|
|
Test = Tail.Substring(OpenParenIndex + 1, CloseParenIndex - OpenParenIndex - 1);
|
|
LogError("Automated test failed ({0}).", Test);
|
|
LastAutoFailIndex = FailIndex;
|
|
}
|
|
}
|
|
}
|
|
// Detect commandlet failure
|
|
else if (bCommandlet)
|
|
{
|
|
const string ResultLog = "Commandlet->Main return this error code: ";
|
|
|
|
int ResultStart = AllClientOutput.LastIndexOf(ResultLog);
|
|
int ResultValIdx = ResultStart + ResultLog.Length;
|
|
|
|
if (ResultStart >= 0 && ResultValIdx < AllClientOutput.Length &&
|
|
AllClientOutput.Substring(ResultValIdx, 1) == "1")
|
|
{
|
|
// Parse the full commandlet warning/error summary
|
|
string FullSummary = "";
|
|
int SummaryStart = AllClientOutput.LastIndexOf("Warning/Error Summary");
|
|
|
|
if (SummaryStart >= 0 && SummaryStart < ResultStart)
|
|
{
|
|
FullSummary = AllClientOutput.Substring(SummaryStart, ResultStart - SummaryStart);
|
|
}
|
|
|
|
|
|
if (FullSummary.Length > 0)
|
|
{
|
|
LogError("Commandlet failed, summary:" + Environment.NewLine +
|
|
FullSummary);
|
|
}
|
|
else
|
|
{
|
|
LogError("Commandlet failed.");
|
|
}
|
|
}
|
|
}
|
|
}
|
|
else if (bClientExited && (DateTime.UtcNow - ExitTime).TotalSeconds > 30)
|
|
{
|
|
Log("Client exited and has been quiet for 30 seconds...exiting");
|
|
bKeepReading = false;
|
|
}
|
|
}
|
|
if (ClientProcess != null && !ClientProcess.HasExited)
|
|
{
|
|
Log("Client is supposed to exit, lets wait a while for it to exit naturally...");
|
|
for (int i = 0; i < 120 && !ClientProcess.HasExited; i++)
|
|
{
|
|
Thread.Sleep(1000);
|
|
}
|
|
}
|
|
if (ClientProcess != null && !ClientProcess.HasExited)
|
|
{
|
|
Log("Stopping client...");
|
|
ClientProcess.StopProcess();
|
|
Thread.Sleep(10000);
|
|
}
|
|
while (ClientLogReader != null && !ClientLogReader.EndOfStream)
|
|
{
|
|
string ClientOutput = ClientLogReader.ReadToEnd();
|
|
if (!String.IsNullOrEmpty(ClientOutput))
|
|
{
|
|
Console.Write(ClientOutput);
|
|
}
|
|
}
|
|
|
|
if (!WelcomedCorrectly)
|
|
{
|
|
throw new AutomationException("Client exited before we asked it to.");
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
var SC = DeployContextList[0];
|
|
IProcessResult ClientProcess = SC.StageTargetPlatform.RunClient(ClientRunFlags, ClientApp, ClientCmdLine, Params);
|
|
if (ClientProcess != null)
|
|
{
|
|
// If the client runs without StdOut redirect we're going to read the log output directly from log file on
|
|
// a separate thread.
|
|
if ((ClientRunFlags & ERunOptions.NoStdOutRedirect) == ERunOptions.NoStdOutRedirect)
|
|
{
|
|
ClientLogReaderThread = new System.Threading.Thread(ClientLogReaderProc);
|
|
ClientLogReaderThread.Start(new object[] { ClientLogFile, ClientProcess });
|
|
}
|
|
|
|
do
|
|
{
|
|
Thread.Sleep(100);
|
|
}
|
|
while (ClientProcess.HasExited == false);
|
|
|
|
SC.StageTargetPlatform.PostRunClient(ClientProcess, Params);
|
|
|
|
// any non-zero exit code should propagate an exception. The Virtual function above may have
|
|
// already thrown a more specific exception or given a more specific ErrorCode, but this catches the rest.
|
|
if (ClientProcess.ExitCode != 0)
|
|
{
|
|
throw new AutomationException("Client exited with error code: " + ClientProcess.ExitCode);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
private static void RunClientWithServer(List<DeploymentContext> DeployContextList, string ServerLogFile, IProcessResult ServerProcess, string ClientApp, string ClientCmdLine, ERunOptions ClientRunFlags, string ClientLogFile, ProjectParams Params)
|
|
{
|
|
IProcessResult ClientProcess = null;
|
|
var OtherClients = new List<IProcessResult>();
|
|
|
|
bool WelcomedCorrectly = false;
|
|
int NumClients = Params.NumClients;
|
|
string AllClientOutput = "";
|
|
int LastAutoFailIndex = -1;
|
|
|
|
if (Params.Unattended)
|
|
{
|
|
string LookFor = "Bringing up level for play took";
|
|
if (Params.DedicatedServer)
|
|
{
|
|
LookFor = "Welcomed by server";
|
|
}
|
|
else if (Params.RunAutomationTest != "")
|
|
{
|
|
LookFor = "Automation Test Succeeded";
|
|
}
|
|
else if (Params.RunAutomationTests)
|
|
{
|
|
LookFor = "Automation Test Queue Empty";
|
|
}
|
|
{
|
|
while (!FileExists(ServerLogFile) && !ServerProcess.HasExited)
|
|
{
|
|
Log("Waiting for logging process to start...");
|
|
Thread.Sleep(2000);
|
|
}
|
|
Thread.Sleep(1000);
|
|
|
|
string AllServerOutput = "";
|
|
using (FileStream ProcessLog = File.Open(ServerLogFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite))
|
|
{
|
|
StreamReader LogReader = new StreamReader(ProcessLog);
|
|
bool bKeepReading = true;
|
|
|
|
FileStream ClientProcessLog = null;
|
|
StreamReader ClientLogReader = null;
|
|
|
|
// Read until the process has exited.
|
|
while (!ServerProcess.HasExited && bKeepReading)
|
|
{
|
|
while (!LogReader.EndOfStream && bKeepReading && ClientProcess == null)
|
|
{
|
|
string Output = LogReader.ReadToEnd();
|
|
if (!String.IsNullOrEmpty(Output))
|
|
{
|
|
AllServerOutput += Output;
|
|
if (ClientProcess == null &&
|
|
(AllServerOutput.Contains("Game Engine Initialized") || AllServerOutput.Contains("Unreal Network File Server is ready")))
|
|
{
|
|
Log("Starting Client for unattended test....");
|
|
ClientProcess = Run(ClientApp, ClientCmdLine + " -testexit=\"" + LookFor + "\"", null, ClientRunFlags | ERunOptions.NoWaitForExit);
|
|
//@todo no testing is done on these
|
|
if (NumClients > 1 && NumClients < 9)
|
|
{
|
|
for (int i = 1; i < NumClients; i++)
|
|
{
|
|
Log("Starting Extra Client....");
|
|
OtherClients.Add(Run(ClientApp, ClientCmdLine, null, ClientRunFlags | ERunOptions.NoWaitForExit));
|
|
}
|
|
}
|
|
while (!FileExists(ClientLogFile) && !ClientProcess.HasExited)
|
|
{
|
|
Log("Waiting for client logging process to start...{0}", ClientLogFile);
|
|
Thread.Sleep(2000);
|
|
}
|
|
if (!ClientProcess.HasExited)
|
|
{
|
|
Thread.Sleep(2000);
|
|
Log("Client logging process started...{0}", ClientLogFile);
|
|
ClientProcessLog = File.Open(ClientLogFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
|
|
ClientLogReader = new StreamReader(ClientProcessLog);
|
|
}
|
|
}
|
|
else if (ClientProcess == null && !ServerProcess.HasExited)
|
|
{
|
|
Log("Waiting for server to start....");
|
|
Thread.Sleep(2000);
|
|
}
|
|
if (ClientProcess != null && ClientProcess.HasExited)
|
|
{
|
|
ServerProcess.StopProcess();
|
|
throw new AutomationException("Client exited before we asked it to.");
|
|
}
|
|
}
|
|
}
|
|
if (ClientLogReader != null)
|
|
{
|
|
if (ClientProcess.HasExited)
|
|
{
|
|
ServerProcess.StopProcess();
|
|
throw new AutomationException("Client exited or closed the log before we asked it to.");
|
|
}
|
|
while (!ClientProcess.HasExited && !ServerProcess.HasExited && bKeepReading)
|
|
{
|
|
while (!ClientLogReader.EndOfStream && bKeepReading && !ServerProcess.HasExited && !ClientProcess.HasExited)
|
|
{
|
|
string ClientOutput = ClientLogReader.ReadToEnd();
|
|
if (!String.IsNullOrEmpty(ClientOutput))
|
|
{
|
|
AllClientOutput += ClientOutput;
|
|
Console.Write(ClientOutput);
|
|
|
|
if (AllClientOutput.LastIndexOf(LookFor) > AllClientOutput.IndexOf(LookFor))
|
|
{
|
|
if (Params.FakeClient)
|
|
{
|
|
Log("Welcomed by server or client loaded, lets wait ten minutes...");
|
|
Thread.Sleep(60000 * 10);
|
|
}
|
|
else
|
|
{
|
|
Log("Welcomed by server or client loaded, lets wait 30 seconds...");
|
|
Thread.Sleep(30000);
|
|
}
|
|
WelcomedCorrectly = true;
|
|
bKeepReading = false;
|
|
}
|
|
else if (Params.RunAutomationTests)
|
|
{
|
|
int FailIndex = AllClientOutput.LastIndexOf("Automation Test Failed");
|
|
int ParenIndex = AllClientOutput.LastIndexOf(")");
|
|
if (FailIndex >= 0 && ParenIndex > FailIndex && FailIndex > LastAutoFailIndex)
|
|
{
|
|
string Tail = AllClientOutput.Substring(FailIndex);
|
|
int CloseParenIndex = Tail.IndexOf(")");
|
|
int OpenParenIndex = Tail.IndexOf("(");
|
|
string Test = "";
|
|
if (OpenParenIndex >= 0 && CloseParenIndex > OpenParenIndex)
|
|
{
|
|
Test = Tail.Substring(OpenParenIndex + 1, CloseParenIndex - OpenParenIndex - 1);
|
|
LogError("Automated test failed ({0}).", Test);
|
|
LastAutoFailIndex = FailIndex;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
|
|
LogFileReaderProcess(ServerLogFile, ServerProcess, (string Output) =>
|
|
{
|
|
bool bKeepReading = true;
|
|
if (ClientProcess == null && !String.IsNullOrEmpty(Output))
|
|
{
|
|
AllClientOutput += Output;
|
|
if (ClientProcess == null && (AllClientOutput.Contains("Game Engine Initialized") || AllClientOutput.Contains("Unreal Network File Server is ready")))
|
|
{
|
|
Log("Starting Client....");
|
|
var SC = DeployContextList[0];
|
|
ClientProcess = SC.StageTargetPlatform.RunClient(ClientRunFlags | ERunOptions.NoWaitForExit, ClientApp, ClientCmdLine, Params);
|
|
// ClientProcess = Run(ClientApp, ClientCmdLine, null, ClientRunFlags | ERunOptions.NoWaitForExit);
|
|
if (NumClients > 1 && NumClients < 9)
|
|
{
|
|
for (int i = 1; i < NumClients; i++)
|
|
{
|
|
Log("Starting Extra Client....");
|
|
IProcessResult NewClient = SC.StageTargetPlatform.RunClient(ClientRunFlags | ERunOptions.NoWaitForExit, ClientApp, ClientCmdLine, Params);
|
|
OtherClients.Add(NewClient);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
else if (ClientProcess == null && !ServerProcess.HasExited)
|
|
{
|
|
Log("Waiting for server to start....");
|
|
Thread.Sleep(2000);
|
|
}
|
|
|
|
if (String.IsNullOrEmpty(Output) == false)
|
|
{
|
|
Console.Write(Output);
|
|
}
|
|
|
|
if (ClientProcess != null && ClientProcess.HasExited)
|
|
{
|
|
|
|
Log("Client exited, stopping server....");
|
|
if (!GlobalCommandLine.NoKill)
|
|
{
|
|
ServerProcess.StopProcess();
|
|
}
|
|
bKeepReading = false;
|
|
}
|
|
|
|
return bKeepReading; // Keep reading
|
|
});
|
|
}
|
|
Log("Server exited....");
|
|
if (ClientProcess != null && !ClientProcess.HasExited)
|
|
{
|
|
ClientProcess.StopProcess();
|
|
}
|
|
foreach (var OtherClient in OtherClients)
|
|
{
|
|
if (OtherClient != null && !OtherClient.HasExited)
|
|
{
|
|
OtherClient.StopProcess();
|
|
}
|
|
}
|
|
if (Params.Unattended)
|
|
{
|
|
if (!WelcomedCorrectly)
|
|
{
|
|
throw new AutomationException("Server or client exited before we asked it to.");
|
|
}
|
|
}
|
|
}
|
|
|
|
private static void SetupClientParams(List<DeploymentContext> DeployContextList, ProjectParams Params, string ClientLogFile, out ERunOptions ClientRunFlags, out string ClientApp, out string ClientCmdLine)
|
|
{
|
|
if (Params.ClientTargetPlatforms.Count == 0)
|
|
{
|
|
throw new AutomationException("No ClientTargetPlatform set for SetupClientParams.");
|
|
}
|
|
|
|
// var DeployContextList = CreateDeploymentContext(Params, false);
|
|
|
|
if (DeployContextList.Count == 0)
|
|
{
|
|
throw new AutomationException("No DeployContextList for SetupClientParams.");
|
|
}
|
|
|
|
var SC = DeployContextList[0];
|
|
|
|
// Get client app name and command line.
|
|
ClientRunFlags = ERunOptions.AllowSpew | ERunOptions.AppMustExist;
|
|
ClientApp = "";
|
|
ClientCmdLine = "";
|
|
string TempCmdLine = "";
|
|
var PlatformName = Params.ClientTargetPlatforms[0].ToString();
|
|
if (Params.Cook || Params.CookOnTheFly)
|
|
{
|
|
List<string> Exes = SC.StageTargetPlatform.GetExecutableNames(SC, true);
|
|
ClientApp = Exes[0];
|
|
if (SC.StageTargetPlatform.PlatformType != UnrealTargetPlatform.IOS)
|
|
{
|
|
TempCmdLine += SC.ProjectArgForCommandLines + " ";
|
|
}
|
|
TempCmdLine += Params.MapToRun + " ";
|
|
|
|
if (Params.CookOnTheFly || Params.FileServer)
|
|
{
|
|
TempCmdLine += "-filehostip=";
|
|
bool FirstParam = true;
|
|
if (UnrealBuildTool.BuildHostPlatform.Current.Platform == UnrealTargetPlatform.Mac)
|
|
{
|
|
NetworkInterface[] Interfaces = NetworkInterface.GetAllNetworkInterfaces();
|
|
foreach (NetworkInterface adapter in Interfaces)
|
|
{
|
|
if (adapter.NetworkInterfaceType != NetworkInterfaceType.Loopback)
|
|
{
|
|
IPInterfaceProperties IP = adapter.GetIPProperties();
|
|
for (int Index = 0; Index < IP.UnicastAddresses.Count; ++Index)
|
|
{
|
|
if (IP.UnicastAddresses[Index].IsDnsEligible && IP.UnicastAddresses[Index].Address.AddressFamily == System.Net.Sockets.AddressFamily.InterNetwork)
|
|
{
|
|
if (!IsNullOrEmpty(Params.Port))
|
|
{
|
|
foreach (var Port in Params.Port)
|
|
{
|
|
if (!FirstParam)
|
|
{
|
|
TempCmdLine += "+";
|
|
}
|
|
FirstParam = false;
|
|
string[] PortProtocol = Port.Split(new char[] { ':' });
|
|
if (PortProtocol.Length > 1)
|
|
{
|
|
TempCmdLine += String.Format("{0}://{1}:{2}", PortProtocol[0], IP.UnicastAddresses[Index].Address.ToString(), PortProtocol[1]);
|
|
}
|
|
else
|
|
{
|
|
TempCmdLine += IP.UnicastAddresses[Index].Address.ToString();
|
|
TempCmdLine += ":";
|
|
TempCmdLine += Params.Port;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (!FirstParam)
|
|
{
|
|
TempCmdLine += "+";
|
|
}
|
|
FirstParam = false;
|
|
|
|
// use default port
|
|
TempCmdLine += IP.UnicastAddresses[Index].Address.ToString();
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
NetworkInterface[] Interfaces = NetworkInterface.GetAllNetworkInterfaces();
|
|
foreach (NetworkInterface adapter in Interfaces)
|
|
{
|
|
if (adapter.OperationalStatus == OperationalStatus.Up)
|
|
{
|
|
IPInterfaceProperties IP = adapter.GetIPProperties();
|
|
for (int Index = 0; Index < IP.UnicastAddresses.Count; ++Index)
|
|
{
|
|
if (IP.UnicastAddresses[Index].IsDnsEligible)
|
|
{
|
|
if (!IsNullOrEmpty(Params.Port))
|
|
{
|
|
foreach (var Port in Params.Port)
|
|
{
|
|
if (!FirstParam)
|
|
{
|
|
TempCmdLine += "+";
|
|
}
|
|
FirstParam = false;
|
|
string[] PortProtocol = Port.Split(new char[] { ':' });
|
|
if (PortProtocol.Length > 1)
|
|
{
|
|
TempCmdLine += String.Format("{0}://{1}:{2}", PortProtocol[0], IP.UnicastAddresses[Index].Address.ToString(), PortProtocol[1]);
|
|
}
|
|
else
|
|
{
|
|
TempCmdLine += IP.UnicastAddresses[Index].Address.ToString();
|
|
TempCmdLine += ":";
|
|
TempCmdLine += Params.Port;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (!FirstParam)
|
|
{
|
|
TempCmdLine += "+";
|
|
}
|
|
FirstParam = false;
|
|
|
|
// use default port
|
|
TempCmdLine += IP.UnicastAddresses[Index].Address.ToString();
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
const string LocalHost = "127.0.0.1";
|
|
|
|
if (!IsNullOrEmpty(Params.Port))
|
|
{
|
|
foreach (var Port in Params.Port)
|
|
{
|
|
if (!FirstParam)
|
|
{
|
|
TempCmdLine += "+";
|
|
}
|
|
FirstParam = false;
|
|
string[] PortProtocol = Port.Split(new char[] { ':' });
|
|
if (PortProtocol.Length > 1)
|
|
{
|
|
TempCmdLine += String.Format("{0}://{1}:{2}", PortProtocol[0], LocalHost, PortProtocol[1]);
|
|
}
|
|
else
|
|
{
|
|
TempCmdLine += LocalHost;
|
|
TempCmdLine += ":";
|
|
TempCmdLine += Params.Port;
|
|
}
|
|
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (!FirstParam)
|
|
{
|
|
TempCmdLine += "+";
|
|
}
|
|
FirstParam = false;
|
|
|
|
// use default port
|
|
TempCmdLine += LocalHost;
|
|
}
|
|
TempCmdLine += " ";
|
|
|
|
if (Params.CookOnTheFlyStreaming)
|
|
{
|
|
TempCmdLine += "-streaming ";
|
|
}
|
|
else if (SC.StageTargetPlatform.PlatformType != UnrealTargetPlatform.IOS)
|
|
{
|
|
// per josh, allowcaching is deprecated/doesn't make sense for iOS.
|
|
TempCmdLine += "-allowcaching ";
|
|
}
|
|
}
|
|
else if (Params.UsePak(SC.StageTargetPlatform))
|
|
{
|
|
if (Params.SignedPak)
|
|
{
|
|
TempCmdLine += "-signedpak ";
|
|
}
|
|
else
|
|
{
|
|
TempCmdLine += "-pak ";
|
|
}
|
|
}
|
|
else if (!Params.Stage)
|
|
{
|
|
var SandboxPath = CombinePaths(SC.RuntimeProjectRootDir, "Saved", "Cooked", SC.CookPlatform);
|
|
if (!SC.StageTargetPlatform.LaunchViaUFE)
|
|
{
|
|
TempCmdLine += "-sandbox=" + CommandUtils.MakePathSafeToUseWithCommandLine(SandboxPath) + " ";
|
|
}
|
|
else
|
|
{
|
|
TempCmdLine += "-sandbox=\'" + SandboxPath + "\' ";
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
ClientApp = CombinePaths(CmdEnv.LocalRoot, "Engine/Binaries", PlatformName, "UE4Editor.exe");
|
|
TempCmdLine += SC.ProjectArgForCommandLines + " ";
|
|
if (!Params.EditorTest)
|
|
{
|
|
TempCmdLine += "-game " + Params.MapToRun + " ";
|
|
}
|
|
else
|
|
{
|
|
TempCmdLine += Params.MapToRun + " ";
|
|
}
|
|
}
|
|
if (Params.LogWindow)
|
|
{
|
|
// Without NoStdOutRedirect '-log' doesn't log anything to the window
|
|
ClientRunFlags |= ERunOptions.NoStdOutRedirect;
|
|
TempCmdLine += "-log ";
|
|
}
|
|
else
|
|
{
|
|
TempCmdLine += "-stdout ";
|
|
}
|
|
if (Params.Unattended)
|
|
{
|
|
TempCmdLine += "-unattended ";
|
|
}
|
|
if (IsBuildMachine || Params.Unattended)
|
|
{
|
|
TempCmdLine += "-buildmachine ";
|
|
}
|
|
if (Params.CrashIndex > 0)
|
|
{
|
|
int RealIndex = Params.CrashIndex - 1;
|
|
if (RealIndex < 0 || RealIndex >= CrashCommands.Count())
|
|
{
|
|
throw new AutomationException("CrashIndex {0} is out of range...max={1}", Params.CrashIndex, CrashCommands.Count());
|
|
}
|
|
TempCmdLine += String.Format("-execcmds=\"debug {0}\" ", CrashCommands[RealIndex]);
|
|
}
|
|
else if (Params.RunAutomationTest != "")
|
|
{
|
|
TempCmdLine += "-execcmds=\"automation list;runtests " + Params.RunAutomationTest + "\" ";
|
|
}
|
|
else if (Params.RunAutomationTests)
|
|
{
|
|
TempCmdLine += "-execcmds=\"automation list;runall\" ";
|
|
}
|
|
if (SC.StageTargetPlatform.UseAbsLog)
|
|
{
|
|
TempCmdLine += "-abslog=" + CommandUtils.MakePathSafeToUseWithCommandLine(ClientLogFile) + " ";
|
|
}
|
|
if (SC.StageTargetPlatform.PlatformType != UnrealTargetPlatform.IOS && SC.StageTargetPlatform.PlatformType != UnrealTargetPlatform.Linux)
|
|
{
|
|
TempCmdLine += "-Messaging -nomcp -Windowed ";
|
|
}
|
|
else
|
|
{
|
|
// skip arguments which don't make sense for iOS
|
|
TempCmdLine += "-Messaging ";
|
|
}
|
|
if (Params.NullRHI && SC.StageTargetPlatform.PlatformType != UnrealTargetPlatform.Mac) // all macs have GPUs, and currently the mac dies with nullrhi
|
|
{
|
|
TempCmdLine += "-nullrhi ";
|
|
}
|
|
if (Params.Deploy && !Params.CookOnTheFly && (SC.StageTargetPlatform.PlatformType == UnrealTargetPlatform.PS4))
|
|
{
|
|
TempCmdLine += "-deployedbuild ";
|
|
}
|
|
|
|
TempCmdLine += "-CrashForUAT ";
|
|
TempCmdLine += Params.RunCommandline;
|
|
|
|
// todo: move this into the platform
|
|
if (SC.StageTargetPlatform.LaunchViaUFE)
|
|
{
|
|
ClientCmdLine = "-run=Launch ";
|
|
ClientCmdLine += "-Device=" + Params.Devices[0];
|
|
for (int DeviceIndex = 1; DeviceIndex < Params.Devices.Count; DeviceIndex++)
|
|
{
|
|
ClientCmdLine += "+" + Params.Devices[DeviceIndex];
|
|
}
|
|
ClientCmdLine += " ";
|
|
ClientCmdLine += "-Exe=\"" + ClientApp + "\" ";
|
|
ClientCmdLine += "-Targetplatform=" + Params.ClientTargetPlatforms[0].ToString() + " ";
|
|
ClientCmdLine += "-Params=\"" + TempCmdLine + "\"";
|
|
ClientApp = CombinePaths(CmdEnv.LocalRoot, "Engine/Binaries/Win64/UnrealFrontend.exe");
|
|
|
|
Log("Launching via UFE:");
|
|
Log("\tClientCmdLine: " + ClientCmdLine + "");
|
|
}
|
|
else
|
|
{
|
|
ClientCmdLine = TempCmdLine;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Client Thread
|
|
|
|
private static void ClientLogReaderProc(object ArgsContainer)
|
|
{
|
|
var Args = ArgsContainer as object[];
|
|
var ClientLogFile = (string)Args[0];
|
|
var ClientProcess = (IProcessResult)Args[1];
|
|
LogFileReaderProcess(ClientLogFile, ClientProcess, (string Output) =>
|
|
{
|
|
if (String.IsNullOrEmpty(Output) == false)
|
|
{
|
|
Log(Output);
|
|
}
|
|
return true;
|
|
});
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Servers
|
|
|
|
private static IProcessResult RunDedicatedServer(ProjectParams Params, string ServerLogFile, string AdditionalCommandLine)
|
|
{
|
|
ProjectParams ServerParams = new ProjectParams(Params);
|
|
ServerParams.Devices = new ParamList<string>(Params.ServerDevice);
|
|
|
|
if (ServerParams.ServerTargetPlatforms.Count == 0)
|
|
{
|
|
throw new AutomationException("No ServerTargetPlatform set for RunDedicatedServer.");
|
|
}
|
|
|
|
var DeployContextList = CreateDeploymentContext(ServerParams, true);
|
|
|
|
if (DeployContextList.Count == 0)
|
|
{
|
|
throw new AutomationException("No DeployContextList for RunDedicatedServer.");
|
|
}
|
|
|
|
var SC = DeployContextList[0];
|
|
|
|
var ServerApp = CombinePaths(CmdEnv.LocalRoot, "Engine/Binaries/Win64/UE4Editor.exe");
|
|
if (ServerParams.Cook)
|
|
{
|
|
List<string> Exes = SC.StageTargetPlatform.GetExecutableNames(SC);
|
|
ServerApp = Exes[0];
|
|
}
|
|
var Args = ServerParams.Cook ? "" : (SC.ProjectArgForCommandLines + " ");
|
|
Console.WriteLine(Params.ServerDeviceAddress);
|
|
TargetPlatformDescriptor ServerPlatformDesc = ServerParams.ServerTargetPlatforms[0];
|
|
if (ServerParams.Cook && ServerPlatformDesc.Type == UnrealTargetPlatform.Linux && !String.IsNullOrEmpty(ServerParams.ServerDeviceAddress))
|
|
{
|
|
ServerApp = @"C:\Windows\system32\cmd.exe";
|
|
|
|
string plinkPath = CombinePaths(Environment.GetEnvironmentVariable("LINUX_ROOT"), "bin/PLINK.exe ");
|
|
string exePath = CombinePaths(SC.ShortProjectName, "Binaries", ServerPlatformDesc.Type.ToString(), SC.ShortProjectName + "Server");
|
|
if (ServerParams.ServerConfigsToBuild[0] != UnrealTargetConfiguration.Development)
|
|
{
|
|
exePath += "-" + ServerPlatformDesc.Type.ToString() + "-" + ServerParams.ServerConfigsToBuild[0].ToString();
|
|
}
|
|
exePath = CombinePaths("LinuxServer", exePath.ToLower()).Replace("\\", "/");
|
|
Args = String.Format("/k {0} -batch -ssh -t -i {1} {2}@{3} {4} {5} {6} -server -Messaging", plinkPath, ServerParams.DevicePassword, ServerParams.DeviceUsername, ServerParams.ServerDeviceAddress, exePath, Args, ServerParams.MapToRun);
|
|
}
|
|
else
|
|
{
|
|
var Map = ServerParams.MapToRun;
|
|
if (!String.IsNullOrEmpty(ServerParams.AdditionalServerMapParams))
|
|
{
|
|
Map += ServerParams.AdditionalServerMapParams;
|
|
}
|
|
if (Params.FakeClient)
|
|
{
|
|
Map += "?fake";
|
|
}
|
|
Args += String.Format("{0} -server -abslog={1} -log -Messaging", Map, CommandUtils.MakePathSafeToUseWithCommandLine(ServerLogFile));
|
|
if (Params.Unattended)
|
|
{
|
|
Args += " -unattended";
|
|
}
|
|
// Do not blindly add -nomcp, only do so if the client is using it
|
|
if (Params.RunCommandline.Contains("-nomcp"))
|
|
{
|
|
Args += " -nomcp";
|
|
}
|
|
|
|
if (Params.ServerCommandline.Length > 0)
|
|
{
|
|
Args += " " + Params.ServerCommandline;
|
|
}
|
|
}
|
|
|
|
if (ServerParams.UsePak(SC.StageTargetPlatform))
|
|
{
|
|
if (ServerParams.SignedPak)
|
|
{
|
|
Args += " -signedpak";
|
|
}
|
|
else
|
|
{
|
|
Args += " -pak";
|
|
}
|
|
}
|
|
if (IsBuildMachine || Params.Unattended)
|
|
{
|
|
Args += " -buildmachine";
|
|
}
|
|
Args += " -CrashForUAT";
|
|
Args += " " + AdditionalCommandLine;
|
|
|
|
|
|
if (ServerParams.Cook && ServerPlatformDesc.Type == UnrealTargetPlatform.Linux && !String.IsNullOrEmpty(ServerParams.ServerDeviceAddress))
|
|
{
|
|
Args += String.Format(" 2>&1 > {0}", ServerLogFile);
|
|
}
|
|
|
|
PushDir(Path.GetDirectoryName(ServerApp));
|
|
var Result = Run(ServerApp, Args, null, ERunOptions.AllowSpew | ERunOptions.NoWaitForExit | ERunOptions.AppMustExist | ERunOptions.NoStdOutRedirect);
|
|
PopDir();
|
|
|
|
return Result;
|
|
}
|
|
|
|
private static IProcessResult RunCookOnTheFlyServer(FileReference ProjectName, string ServerLogFile, string TargetPlatform, string AdditionalCommandLine)
|
|
{
|
|
var ServerApp = HostPlatform.Current.GetUE4ExePath("UE4Editor.exe");
|
|
var Args = String.Format("{0} -run=cook -cookonthefly -unattended -CrashForUAT -log",
|
|
CommandUtils.MakePathSafeToUseWithCommandLine(ProjectName.FullName));
|
|
if (!String.IsNullOrEmpty(ServerLogFile))
|
|
{
|
|
Args += " -abslog=" + CommandUtils.MakePathSafeToUseWithCommandLine(ServerLogFile);
|
|
}
|
|
if (IsBuildMachine)
|
|
{
|
|
Args += " -buildmachine";
|
|
}
|
|
Args += " " + AdditionalCommandLine;
|
|
|
|
// Run the server (Without NoStdOutRedirect -log doesn't log anything to the window)
|
|
PushDir(Path.GetDirectoryName(ServerApp));
|
|
var Result = Run(ServerApp, Args, null, ERunOptions.AllowSpew | ERunOptions.NoWaitForExit | ERunOptions.AppMustExist | ERunOptions.NoStdOutRedirect);
|
|
PopDir();
|
|
return Result;
|
|
}
|
|
|
|
private static IProcessResult RunFileServer(ProjectParams Params, string ServerLogFile, string AdditionalCommandLine)
|
|
{
|
|
#if false
|
|
// this section of code would provide UFS with a more accurate file mapping
|
|
var SC = new StagingContext(Params, false);
|
|
CreateStagingManifest(SC);
|
|
MaybeConvertToLowerCase(Params, SC);
|
|
var UnrealFileServerResponseFile = new List<string>();
|
|
|
|
foreach (var Pair in SC.UFSStagingFiles)
|
|
{
|
|
string Src = Pair.Key;
|
|
string Dest = Pair.Value;
|
|
|
|
Dest = CombinePaths(PathSeparator.Slash, SC.UnrealFileServerInternalRoot, Dest);
|
|
|
|
UnrealFileServerResponseFile.Add("\"" + Src + "\" \"" + Dest + "\"");
|
|
}
|
|
|
|
|
|
string UnrealFileServerResponseFileName = CombinePaths(CmdEnv.LogFolder, "UnrealFileServerList.txt");
|
|
File.WriteAllLines(UnrealFileServerResponseFileName, UnrealFileServerResponseFile);
|
|
#endif
|
|
var UnrealFileServerExe = HostPlatform.Current.GetUE4ExePath("UnrealFileServer.exe");
|
|
|
|
Log("Running UnrealFileServer *******");
|
|
var Args = String.Format("{0} -abslog={1} -unattended -CrashForUAT -log {2}",
|
|
CommandUtils.MakePathSafeToUseWithCommandLine(Params.RawProjectPath.FullName),
|
|
CommandUtils.MakePathSafeToUseWithCommandLine(ServerLogFile),
|
|
AdditionalCommandLine);
|
|
if (IsBuildMachine)
|
|
{
|
|
Args += " -buildmachine";
|
|
}
|
|
PushDir(Path.GetDirectoryName(UnrealFileServerExe));
|
|
var Result = Run(UnrealFileServerExe, Args, null, ERunOptions.AllowSpew | ERunOptions.NoWaitForExit | ERunOptions.AppMustExist | ERunOptions.NoStdOutRedirect);
|
|
PopDir();
|
|
return Result;
|
|
}
|
|
|
|
#endregion
|
|
}
|