SteamDB

» » Декомпиляция заскриптованного кода unreal engine 2.5 (Killing floor).

Декомпиляция заскриптованного кода unreal engine 2.5 (Killing floor).

Декомпиляция заскриптованного кода unreal engine 2.5 (Killing floor).


1.



Для этой процедуры нам понадобиться две программы: HexEdit для правки шестнадцатеричного кода и UT Package Tool v2.0 beta 5, который собственно и декомпилирует код с удаленным текстом исходного кода. Так же рекомендую программу UnCodeX для удобного просмотра и поиска нужной функции в исходниках Killing Floor (которые загружаются вместе с редактором Killing Floor SDK). Берем зашифрованный файл (обычно это *.u файлы ), который нужно декомпилить, и для начала декомпилируем его обычными средствами Killing Floor (ucc.exe), для того чтоб получить defaultproperties, так как программа UT Package Tool декомпилит эти значения по умолчанию с некоторыми ошибками. Для этого создаем в папке System bat файл, в котором пишем ucc batchexport Mut.u class uc ..MutClassespauseВместо Mut имя вашего заскриптованного файла. Сохраняем. Запускаем. Сохраняем полученные *.uc файлы к примеру в папке под именем Default.





2.



Далее опять же исходный *.u файл открываем в HexEdit и меняем первый байт значение которого C2 на значение C1, для того чтоб UT Package Tool определил этот файл как файл игры Unreal Tournament 2004, так как программа не знакома с игрой Killing Floor. Сохраняем его в HexEdit. Запускаем UT Package Tool и открываем полученный файл. Во вкладке Export Tree щелкаем на любом классе правой кнопкой и нажимаем Full Collapse. Нажимаем File/Options и убеждаемся, что стоит галочка Add line offsets to decompiled code. Далее по порядку на каждом классе щелкаем правой кнопкой мыши и нажимаем Decompile. В правом окне должен появиться декомпилированный код данного класса. Справа нажимаем Save. Создаем какую-нибудь папку с будущим названием данного мутатора, например Mut, и в этой же папке создаем подпапку Classes, в которой и сохраняем декомпилированный код. Данную процедуру проделываем со всеми классами слева. Далее сохраненные *.uc файлы в папке MutClasses открываем с помощью блокнота и заменяем все defaultproperties на defaultproperties из сохраненной ранее папки Default. Если, например, в описании класса есть class AntiBlocker extends Mutator Localized HideCategories(Movement,Collision,Lighting,LightColor,Karma,Force);то удаляем Localized и HideCategories(Movement,Collision,Lighting,LightColor,Karma,Force). Знак ; оставляем, получается просто class AntiBlocker extends Mutator;





3.



Далее рассмотрим некоторые ошибки и недочеты допущенные самим UT Package Tool. Иногда при компилировании данного дешифрованного кода ucc.exe может выдать, к примеру, следующее сообщение Log: Parsing ClientPerkRepLinkError: E:GamesGameSteamsteamappscommonkillingfloorKFpubModClassesClientPerkRepLink.uc(46) : Error, Unrecognized type 'FPerksListType'Данный класс выглядит следующим образомclass ClientPerkRepLink extends LinkedReplicationInfo;var array<FPerksListType> CachePerks;struct FPerksListType{ var Class<KFpubVet> PerkClass; var byte CurrentLevel;};Тут ошибка в следующем, что UT Package Tool сначала присваивает переменную CachePerks, ссылаясь на переменную FPerksListType, структура которой описывается уже после объявления CachePerks, правильно будет сначала объявить переменную FPerksListType, а затем уже ссылаться на нее, будет такclass ClientPerkRepLink extends LinkedReplicationInfo;struct FPerksListType{ var Class<KFpubVet> PerkClass; var byte CurrentLevel;};var array<FPerksListType> CachePerks;Короче, надо проверить все uc файлы, и перенести все структуры (struct) в начало файла сразу после объявления класса, или на усмотрение самого кодера. Следующая ошибка, которая выпала на одном примере по компиляции взломанного мутатора Log: Parsing ClientPerkRepLinkError: E:GamesGameSteamsteamappscommonkillingfloorKFpubModClassesClientPerkRepLink.uc(290) : Error, Missing '>' in 'class limitor'Ошибка в следующем тексте программы local array<Class<KFpubVet>> ca;Здесь просто надо после local array<Class<KFpubVet> поставить пробел, получитьсяlocal array<Class<KFpubVet> > ca;Далее Log: Parsing KillingFloorPubError: E:GamesGameSteamsteamappscommonkillingfloorKFpubModClassesKillingFloorPub.uc(251) : Error, Unrecognized type 'ServerResponseLine'Текст с ошибкойfunction GetServerDetails (out ServerResponseLine ServerState)Правильно будетfunction GetServerDetails (out GameInfo.ServerResponseLine ServerState)Если компилятор говорит что переменная не найдена, то можно покопаться в исходных кодах Killing Floor и посмотреть правильное написание данной переменной, в данном случае это ServerResponseLine, копируете название, запускаете UnCodeX и в поиске вбиваете эту переменную, и программа покажет возможно правильное написание этой переменной. Некоторые примеры переменных, когда UT Package Tool не прописывает их полностью: PlayerRecord (правильно xUtil.PlayerRecord ), ServerFavorite (правильно ExtendedConsole.ServerFavorite), AllowWeaponInTrader ( правильно Static.AllowWeaponInTrader, по поводу Static, это слово много где будет приписываться по ходу компиляции кода ) .ДалееLog: Parsing KFpubGTError: E:GamesGameSteamsteamappscommonkillingfloorKFpubModClassesKFpubGT.uc(424) : Error, 'Extends' not allowed here: state 'PendingMatch' overrides version in parent classТекст с ошибкойauto state PendingMatch extends PendingMatchПродублировался PendingMatch, просто удаляем и получаемauto state PendingMatchДалееLog: Parsing KFpubTabMidGameVCError: E:GamesGameSteamsteamappscommonkillingfloorKFpubModClassesKFpubTabMidGameVC.uc(20) : Error, Specified type modifiers not allowed hereТекст с ошибкойfunction bool Buttonclicked (export editinlineuse GUIComponent Sender)Правильноfunction bool Buttonclicked ( GUIComponent Sender)Просто удаляем export editinlineuse. Это также касается объявления переменных, напримерlocal export editinlineuse GUIList List;Правильноlocal GUIList List;ДалееLog: Compiling KFpubLCError: E:GamesGameSteamsteamappscommonkillingfloorKFpubModClassesKFpubLC.uc(41) : Error, Type mismatch in 'new' nameТекс с ошибкойC = new (None,Class'KFpubLC');ПравильноC = new (None) Class'KFpubLC';ДалееLog: Compiling KFpubLCError: E:GamesGameSteamsteamappscommonkillingfloorKFpubModClassesKFpubLC.uc(48) : Error, Label 'JL0021' not found in this block of codeТекст с ошибкойstatic final function AddSafeCleanup (PlayerController PC){ local int i; local KFpubLC C; i = PC.Player.LocalInteractions.Length - 1; // 0x00000019 : 0x0000 if ( i >= 0 ) // 0x00000032 : 0x0021 { if ( PC.Player.LocalInteractions[i ].Class == Default.Class ) // 0x0000003B : 0x002C { return; // 0x0000005F : 0x005C } --i; // 0x00000061 : 0x005E goto JL0021; // 0x00000066 : 0x0065 } C = new (None) Class'KFpubLC'; // 0x00000069 : 0x0068 C.ViewportOwner = PC.Player; // 0x00000074 : 0x0077 C.Master = PC.Player.InteractionMaster; // 0x00000089 : 0x0094 i = PC.Player.LocalInteractions.Length; // 0x000000A5 : 0x00BA PC.Player.LocalInteractions.Length = i + 1; // 0x000000BB : 0x00D8 PC.Player.LocalInteractions[i ] = C; // 0x000000D4 : 0x00F9 C.Initialize(); // 0x000000ED : 0x011C}Справа типа надписи как // 0x000000A5 : 0x00BA это адреса, которые прописались при декомпиляции при помощи UT Package Tool ( для этого мы выставили галочку Add line offsets to decompiled code в опциях программы). Сделано это для того, чтоб мы могли видеть куда прописать Label, который нужен для оператора goto. Дело в том, что UT Package Tool все операции с циклами типа как for, while и т.д. декомпилирует в оператор goto, при этом программа всячески отказывается самостоятельно расставлять необходимые Label, а если и расставляет (что очень редко), то всегда не правильно, и их надо удалять, после этого расставлять вручную. На данном примере здесь только один оператор goto который хочет перейти на label JL0021. Правильно будет такstatic final function AddSafeCleanup (PlayerController PC){ local int i; local KFpubLC C; i = PC.Player.LocalInteractions.Length - 1; // 0x00000019 : 0x0000 JL0021: if ( i >= 0 ) // 0x00000032 : 0x0021 { if ( PC.Player.LocalInteractions[i ].Class == Default.Class ) // 0x0000003B : 0x002C { return; // 0x0000005F : 0x005C } --i; // 0x00000061 : 0x005E goto JL0021; // 0x00000066 : 0x0065 } C = new (None) Class'KFpubLC'; // 0x00000069 : 0x0068 C.ViewportOwner = PC.Player; // 0x00000074 : 0x0077 C.Master = PC.Player.InteractionMaster; // 0x00000089 : 0x0094 i = PC.Player.LocalInteractions.Length; // 0x000000A5 : 0x00BA PC.Player.LocalInteractions.Length = i + 1; // 0x000000BB : 0x00D8 PC.Player.LocalInteractions[i ] = C; // 0x000000D4 : 0x00F9 C.Initialize(); // 0x000000ED : 0x011C}Но label нужно прописывать именно в той функции, где используется оператор goto.ДалееLog: Compiling ClientPerkRepLinkError: E:GamesGameSteamsteamappscommonkillingfloorKFpubModClassesClientPerkRepLink.uc(78) : Error, Missing 'Reliable' or 'Unreliable'Текст с ошибкойun?reliable if ( (Role == 4) && bNetOwner )Правильно reliable if ( (Role == 4) && bNetOwner )Так как UT Package Tool не знал, что применить, Reliable или Unreliable. Насколько я понял в этих понятиях о репликации, то Reliable пересылает обязательно переменную или функцию от сервера к клиенту и наоборот, а при случае с Unreliable, допускается утрата переменной или функции при плохом интернет соединении. Так что в большинстве случаев используется именно Reliable.





4.



ДалееLog: Compiling ClientPerkRepLinkError: E:GamesGameSteamsteamappscommonkillingfloorKFpubModClassesClientPerkRepLink.uc(496) : Error, 'If' is not allowed hereТекст с ошибкойif ( Level.NetMode == 3 )Правильноif ( Level.NetMode == NM_Client )Дело в том, что UT Package Tool некоторые символьные значения заменяет цифрами, эти цифры соответствуют некоторым значениям переменных, которые состоят из структур. Это касается таких выражениях как ClientState, ClientGrenadeState, NetMode, Role, Physics, PlayOwnedSound, SetDrawType и многих других, все их можно найти в исходникак Killing Floor, например большинство их описано в классе Actor. Вот таблица некоторых из нихClientState-----------0- WS_None1- WS_Hidden2- WS_BringUp3- WS_PutDown4- WS_ReadyToFireClientGrenadeState------------------0- GN_None1- GN_TempDown2- GN_BringUpNetMode-------0- NM_Standalone1- NM_DedicatedServer2- NM_ListenServer3- NM_ClientRole----0- ROLE_None1- ROLE_DumbProxy2- ROLE_SimulatedProxy3- ROLE_AutonomousProxy4- ROLE_AuthorityPhysics-------0- PHYS_None1- PHYS_Walking2- PHYS_Falling3- PHYS_Swimming4- PHYS_Flying5- PHYS_Rotating6- PHYS_Projectile7- PHYS_Interpolating8- PHYS_MovingBrush9- PHYS_Spider10- PHYS_Trailer11- PHYS_Ladder12- PHYS_RootMotion13- PHYS_Karma14- PHYS_KarmaRagDoll15- PHYS_Hovering16- PHYS_CinMotionPlayOwnedSound--------------0- SLOT_None1- SLOT_Misc2- SLOT_Pain3- SLOT_Interact4- SLOT_Ambient5- SLOT_Talk6- SLOT_InterfaceSetDrawType-----------0- DT_None,1- DT_Sprite,2- DT_Mesh,3- DT_Brush,4- DT_RopeSprite,5- DT_VerticalSprite,6- DT_Terraform,7- DT_SpriteAnimOnce,8- DT_StaticMesh,9- DT_DrawType,10-DT_Particle,11-DT_AntiPortal,12-DT_FluidSurfaceСлева цифра, а справа чему эта цифра будет соответствовать, в нашем примере Level.NetMode == 3 равна три, что соответствует значению NM_Client, поэтому нужно поменять на Level.NetMode == NM_Client, повторяю, все эти значения можно найти в исходниках. Иногда компилятор допускает использование цифр вместо буквенного значения, но все равно, лучше этого не допускать.Далее опять та же ошибка в том же месте, но по другому поводуLog: Compiling ClientPerkRepLinkError: E:GamesGameSteamsteamappscommonkillingfloorKFpubModClassesClientPerkRepLink.uc(496) : Error, 'If' is not allowed hereТекст с ошибкойauto state RepSetup{ if ( Level.NetMode == NM_Client ) // 0x00000018 : 0x0000 { stop // 0x0000002C : 0x0019 }Это не весь код, а только кусочек, где произошла ошибка, ошибка заключается в следующем, программа UT Package Tool в функциях State не хочет расставлять Label, здесь должна быть метка begin, будет правильно выглядеть такauto state RepSetup{Begin: if ( Level.NetMode == NM_Client ) // 0x00000018 : 0x0000 { stop; // 0x0000002C : 0x0019 }Так что в каждом state нужно визуально просмотреть на необходимость нужных меток, а если есть сомнения лучше подглядеть в исходниках, в основном все статы переписываются из уже имеющихся в самой игре. Если этого не сделать, то компилятор может и закончить компиляцию мода без ошибок и предупреждений, но в этом случае возможно наблюдать, что, к примеру, какой-нибудь зомби будет себя вести не адекватно, тупить и так далее, именно из-за того, что мы в стате не прописали нужную метку, почему зомби? Потому что в основном они и используют такие функции как state, но не только они конечно. Если кто-то заметил, то после оператора stop я поставил знак ; это тоже была ошибка допущенная UT Package Tool. Оператор goto нельзя использовать в state, заменяйте выражения на команду while в основном, в этом вам помогут исходники. Например текст с кодом как делать нельзяauto state RepSetup{begin: if ( Level.NetMode == NM_Client ) // 0x00000018 : 0x0000 { stop; // 0x0000002C : 0x0019 } Sleep(1.0); // 0x0000002D : 0x001A NetUpdateFrequency = 0.5; // 0x00000035 : 0x0022 if ( NetConnection(StatObject.PlayerOwner.Player) != None ) // 0x0000003E : 0x002D {if ( (ClientAccknowledged[0] < ShopInventory.Length) || (ClientAccknowledged[1] < ShopCategories.Length) ) // 0x00000057 : 0x004F { SendIndex = 0; // 0x00000075 : 0x0075if ( SendIndex < ShopInventory.Length ) // 0x0000007A : 0x007C { ClientReceiveWeapon(SendIndex,ShopInventory[SendIndex].PC,ShopInventory[SendIndex].CatNum); // 0x00000086 : 0x008C Sleep(0.1); // 0x000000A1 : 0x00B7 ++SendIndex; // 0x000000A9 : 0x00BF goto JL007C; // 0x000000AE : 0x00C6 } SendIndex = 0; // 0x000000B1 : 0x00C9if ( SendIndex < ShopCategories.Length ) // 0x000000B6 : 0x00D0 { ClientReceiveCategory(SendIndex,ShopCategories[SendIndex]); // 0x000000C2 : 0x00E0 Sleep(0.1); // 0x000000D2 : 0x00F8 ++SendIndex; // 0x000000DA : 0x0100 goto JL00D0; // 0x000000DF : 0x0107 } ClientSendAcknowledge(); // 0x000000E2 : 0x010A Sleep(1.0); // 0x000000E6 : 0x0110 goto JL004F; // 0x000000EE : 0x0118 }if ( ClientAckSkinNum < CustomChars.Length ) // 0x000000F1 : 0x011B { ClientReceiveChar(CustomChars[ClientAckSkinNum],ClientAckSkinNum); // 0x000000FD : 0x012B Sleep(0.151); // 0x0000010B : 0x0141 goto JL011B; // 0x00000113 : 0x0149 } } GotoState('None'); // 0x00000116 : 0x014C}И даже если вы тут расставите label, то код не откомпилится. Будет правильно такAuto state RepSetup{Begin: if( Level.NetMode==NM_Client ) Stop; Sleep(1.f); NetUpdateFrequency = 0.5f; if( NetConnection(StatObject.PlayerOwner.Player)!=None ) // Network client. { // Now MAKE SURE client receives the full inventory list. while( ClientAccknowledged[0]<ShopInventory.Length || ClientAccknowledged[1]<ShopCategories.Length ) { for( SendIndex=0; SendIndex<ShopInventory.Length; ++SendIndex ) { ClientReceiveWeapon(SendIndex,ShopInventory[SendIndex].PC,ShopInventory[SendIndex].CatNum); Sleep(0.1f); } for( SendIndex=0; SendIndex<ShopCategories.Length; ++SendIndex ) { ClientReceiveCategory(SendIndex,ShopCategories[SendIndex]); Sleep(0.1f); } ClientSendAcknowledge(); Sleep(1.f); } // Send client all the custom characters. while( ClientAckSkinNum<CustomChars.Length ) { ClientReceiveChar(CustomChars[ClientAckSkinNum],ClientAckSkinNum); Sleep(0.15f); } } GoToState('');}Здесь все goto заменены на while и for.





5.



Здесь не все ошибки, которые допускает программа при декомпиляции, требуется много времени, терпения и внимания, чтоб все их исправить вручную. В основном помогают исходники самой игры, там можно найти почти все переменные, функции и так далее и проследить, где была допущена ошибка. Есть более лучшие программы, чем UT Package Tool, тем более они бесплатны, как со своими плюсами, так и минусы тоже имеются, в другой программе не надо проделывать столько много ручной работы, не надо самому уже прописывать label, копировать defaultproperties и так далее, но жутко смущает один факт, что опять же не правильно расставляет окончания каких-нибудь циклов, условий, это знаки {}, из-за чего код может оказаться далеко не тем, что желали, хотя и меньше работы, а с другой стороны в UT Package Tool намного больше ручной работы, но в то время еще не разу не подводил. Если пытаться декомпилить полностью весь сервер, то это может занять несколько дней, может и неделю таким способом, зависит от сложности самого сервера, но а если говорить о каком-нибудь оружии, зомби, скина, то можно управиться очень даже быстро, при условии, если анимация нужной информации не упакована в большой пак, где удалена информация о мешах, что приводит к невозможности распаковать пак и вытянуть от туда нужную информацию с последующей упаковкой в собственный пак, но это только относиться к анимации, если и существует лекарство, то мне оно не известно. Так или иначе, можно в крайнем случае использовать весь пак, который нельзя распаковать, просто не многие пойдут на то, чтоб использовать один скин из , к примеру, десяти, которые находятся в этом паке. Конечно, можно попытаться удалить всю ненужную информацию с пака средствами Killing Floor SDK, и сохранить только нужную, но опять же, если в этом паке вшит класс, который ссылается на данную анимацию, то SDK скажет, что не может удалить меш, так как она используется.



скачать dle 10.6фильмы бесплатно