Jump to content

Leaderboard

Popular Content

Showing content with the highest reputation on 08/03/18 in all areas

  1. July Digest 2018 The following digest covers the month of July 2018. Staff Changes: None Development Highlights: CORE: Added a 'force' option to attachrid (b3643bfe4) Fixed broken guild notices (b3a51eaa) Fixed logging of #CASHPOINTS and #KAFRAPOINTS (ce9cbd2e) Added possibility to log without attached player (3faf7004) Added support for packet sending map data 0xAC5 (145b60f7) Added Guild Storage Expansion Skill (e13ca63c) Fixed a bug with warlock's spheres (cea5ad71) Corrected SC_MTF_CRIDAMAGE bonus not triggering (6b148d5c) Refactored roulette system (fe7c0a78) Missing returns for inarray and countinarray (500cfdc4) Added empty packet functions for private airship (74efc7d6) Cleaned up Summer 2 code (b2c026d4) Corrected some item bonuses not triggering (fdd24756) Pets should mimic master's walk speed (042b8862) Fixed Guild Storage Expansion skill saving (bfd7af34) Replaced HID timer function parameters in a macro (c4d7dc76) Freezing and Burning can occur at the same time (1a6bc209) Negative MDEF should not increase damage taken from magic (030443c9) Initial Release of Attendance Feature (a5588dd9) Updated max recovery weight to 70% for renewal (b409936f) Resolved Guild Storage Expansion not updating (bbe552d1) Cleaned up the mapflag system (a942853d, 93139226) Fixed missing curly braces in reloadscript (123303ef) Fixing party death icon in newer clients (95c3aed8) Fixed a bug with disable_items script command (6b3f0717) Fixed EXP bug and added failsafe to family check functions (952ac43e) Cleaned up map data storage (584fcac4) Fixes channel command crash (3de9a44f) Initial release of private airship system (8dea04a8) Fixed walk_choices's type (a05ed6e8) DATABASE: Fixed incorrect drop_id in quests (1b72f727) Updated Shield Spell behavior (d612788e) Updated Axe Mastery behavior (20a72e0c) Updated Masquerade effects (f2437f4a) Adjusted Amistr's Defense behavior (3de58247) Adjusted Shield Chain range (eeb01923) Corrected TWO skills according to aegis datas (cd05eb15) Update Airship Assault Monster stats (7717c1e6) Corrected Spiritual Sphere Absorption and Cursed Circle interaction (4f97c749) SCRIPT: Fixed issue with Gunslinger Manual (e4eddc3e) Fixed rate for HD material in shadow refiner npc (f9797109) Added comments in custom quest_shop.txt (84299027) Added extra npc checks (6e8599cd, 6b19b72d) Corrected Archer Training bug (532e043) Added Academy monster re-spawn (4db212bf) Fixed quest warning in quests_amatsu.txt (12f62e63) Implemented Banquet for Heroes ep 16.1 (7a8ac464) Added extra nowarpto on some maps (f1f47091) Fixed npc location for Lutie quest (58eadcda) Fixed a mistake in 2008 headgear quest (fa4021d2) OTHERS: Updated travis script (a8b7476c) Fixed a few compiler warnings on clang (91169d7e) Update tools/config.pl (62ac5be4) Added .editorconfig file to force editor settings for certain file types (3165e521) Statistics: Excluding merges, 11 authors have pushed 76 commits to master and 115 commits to all branches. On master, 194 files have changed and there have been 28,777 additions and 7,054 deletions. 61 Active Pull Requests 66 Active Issues 51 Merged Pull Requests 10 Proposed Pull Requests 49 Closed Issues 17 New Issues List of Contributors: @4144, @admkakaroto, @Akkarinage, @aleos89, @anacondaqq, @Atemo, @AzarthMZintos, @Balferian, @BrOgBr, @cydh, @Daniel4rt, @Daegaladh, @DavidPS92, @ecdarreola, @EthernalFriend, @Everade, @flamefury, @functor-x, @gladio78, @gustavobrigo, @Haikenz, @hendra814, @Kutikuti, @Lemongrass3110, @lRaikeNl, @MrLekkz, @nornane, @RadianFord, @Raf4h, @sader1992, @secretdataz, @spinzaku, @teededung, @tmav94, @uddevil, @V0rr, @vykimo, @yoonjunho72 Show your support to rAthena by submitting your Issue or Pull Requests!
    6 points
  2. This tutorial will leads you to Set multiple char-server as shown as multi services after login in RO Client Set multiple map-servers for 1 char-server A Lazy setup So called Lazy setup because this guide only "copy" the necessary super minimum config file. The Lazy config will runs same server cores, so if server is compiled in renewal, you only can change the rates as example to make different server types (mod, renewal vs pre) you have to copy/separate the rathena files, u will understand if you can understand this basic (... that's what I thought) How to make it no lazy? Just copy the folders, restructure by using decent directory names... so lazy to write it now, maybe later I've seen the setup before, years ago, can't recall where, maybe in old wiki? Because in current wiki is just like this: Multiple Servers. 1 Login-server with Multiple Char-Server 1 login-server set just like your normal setup add 1 more connection account in login (sex = 'S'), the username & password must be different with the first one. Example by default is s1 and p1, this entry be s2 and p2 2 char-servers char-server A set just like your normal setup map-server A.1 set just like normal setup char-server B copy conf/char_athena.conf as conf/char_athena2.conf change the userid: s2 change the passwd: p2 change the server_name: rAthena-2 change the char_port: 6122 map-server B.1 copy conf/map_athena.conf as conf/map_athena2.conf change the userid: s2 change the passwd: p2 change the char_port to match char-server B, 6122 change the map_port: 5122 in addition maybe you later can copy conf/battle/* to conf/battle2/*, so just do this int this example. So you need to copy conf/battle_athena.conf to conf/battle2/battle_athena.conf MySQL Databases DB1 Create database with name (if default is) ragnarok Do normal config, import everything just like normal config DB2 Create database with name ragnarok2 Do normal config, import everything just like normal config inter_athena.conf setup Inter-1 set as normal setup Inter-2 copy conf/inter_athena.conf as conf/inter_athena2.conf set as normal setup change the char_server_id to ragnarok2 change the map_server_id to ragnarok2 change the log_db_id to ragnarok2 Run the servers Run login-server Run char-server A and map-server A1 just like running a server For the 2nd server (char-server B and map-server B.1) follow this You can run manually by open command line or copy the charserv.bat and mapserv.bat file (that's why I against deleting .bat file in compilation), by following char-server.exe--inter-config conf/inter_athena2.conf --char-config conf/char_athena2.conf map-server.exe --inter-config conf/inter_athena2.conf --map-config conf/map_athena2.conf --battle-config conf/battle2/battle_athena.conf 1 Char-Server with Multiple Map-servers By simple examples you want 2nd map-server have towns only And this map-servers are part of Char-Server B be careful between map_athena and maps_athena, there's "s" and there is not. Map-Server B.1 From conf/map_athena2.conf Change import: conf/maps_athena.conf to import: conf/maps_athenaB1.conf Copy conf/maps_athena.conf to conf/maps_athenaB1.conf Remove/comment payon, prontera, izlude, morocc, and other cities from this map-server in file conf/maps_athenaB1.conf Copy npc/script Map-server B.2 Copy conf/map_athena2.conf to conf/map_athena2a.conf Set map_port: 5123 (5121 used for Map-server B.1, while 5122 for B.2) Change import: conf/maps_athenaB1.conf to import: conf/maps_athenaB2.conf Make a new file conf/maps_athenaB2.conf Add the entries map: payon map: prontera map: izlude map: morocc // ... Now re-run the Map-server B2 then following by B3 map-server.exe --inter-config conf/inter_athena2.conf --map-config conf/map_athena2.conf --battle-config conf/battle2/battle_athena.conf map-server.exe --inter-config conf/inter_athena2.conf --map-config conf/map_athena2a.conf --battle-config conf/battle2/battle_athena.conf Your map-servers will be run wil neat error messages because missing NPC LOL. Because map-server will hardcoded-ly reads NPC scripts listing from /npc/[pre-]re/scripts_main.conf, you can redefine the path in config file LOL. That's why I say this setup is lazy, because I lazy to copy 'rathena' dir to another dir > then to give an example to remove unnecesary NPCs Known Multi Server Issues Multi Char-server issues None yet Multi Map-server issues Some atcommands, such who commands Calling player from other map-server, such Emergency Call skill Channel System Guild storage dupe, yeah, never enable (at)gstorage command if you run this mode The rest later, I forgot all topic references Map-server reads scripts_main.conf from same root directory, can redefine Image, video, or any materials to make this tutorial can be fancier, will be added later (so much later....)
    5 points
  3. Briefing & Concept Hello everyone! As you may noticed, by a petition I asked to our staff, we had some changes in this forum. Now it is named as 3D Modeling Showcase, instead of just Map Showcase The idea is to promove the development/discussion in all regards the 3D area. I remember that years before this area was almost null in the *Athena communities, due to a lot of missinformation/resources... not anymore! Back to the thread. This first release (of a lot to come) is in grattitude to a team where I'm member and after 2 years of development and testings, we were able to finally finish our Animated 3D Monsters Project as for now we can handle -bones animations- for gr2 files. Donations are Welcome in appreciation to Ricky92 who developed the Granny Converter. This release is possible thanks by the Granny Animation team: Doss, Ricky92, Olrox, Ai4rei, curiosity, Lemongrass, Shinryo, Yommy, Greenbox You might remember the emperium/guardians/treasure boxes. Yes, those are the kind of mobs/models I'm refering to. In short words, thanks to the work of our team and of course the community support, we can add animation with bones in any 3D model we have. That means for example: make our own 3D mobs, add animation to pre-existing models like a wind a blowing effect to the prontera flags, add interactions like opening gates... etc. Now, lets talk about this release. You may remember "Ragnarok II Gate of the World" a game from Gravity that stopped development some time ago. Well, as a first release of this tool, I took my time to bring some packs of these awesome mobs that you can use in your server now. Some technical info: - This games runs under an Unreal engine - Granny exporter for 3ds max used to import the animations - Granny converter by Ricky92 to convert the gr2 files into RO version About this release So, what do we have new on this release? This first pack, contains 4 full animated 3D mobs from this game. Animations are: Walk, Dead, Attack, Stand and Damage. Just a reminder: The damage animation is not showing for custom 3d mobs even if they have it; this also happens with official 3d mobs aswell. So, we believe it is more a matter of the official client rather than a custom addition to take care of. Some notes you have to consider please. We are still in early state. I mean, it has been years without the possibility to add our own 3D mobs until now! so, a lot of optimizations/details at exporting are in the TODO list. Dead animation is fixed in 2 mobs in this pack that by an unknown reason they made some graphical lag with this animation. It was necessary to fix the end keyframe to the default dead animation in the mob, so, when these two mobs dies, they return to the default position (I can tell this also happens in official mobs, I believe this is a matter of Gravity too) Attack animation: The client, by a reason, shows the attack animation really fast. We must make them lower in max, and export it in gr2 with this in mind. Some glitches like weird rotation in the Y axis, is presented if you export the gr2 models with "relocating position to origin";. I realized this and finally the mobs were not bad rotated by the client. When exporting bones, you must disable: texture and mesh data. By that way, the gr2 will be setted as the official ones, which they only stores the animation without bones mesh/texture data. I know it is nice to have it listed like that. But the true is that it took me HOURS! to do those tests and have those conclutions. Thanks to that, the mobs were fixed and they don't have any serious glitches =P These mobs are compatible and were tested on: 2011-03-15a and 2012-04-10a clients. However, we believe that our feature works also with: "2010-11-24a towards "2011-12-14c" range date, so as "2011-12-20b towards "2012-07-16a" range date aswell. Don't worry, adding the mobs its really easy, just as how you add normal sprites mobs. The only difference is a small patch you have to apply to your current exe. These details will be added in the INSTRUCTION.txt file attached in the download pack of this release. So there you have this animated gifs of them!. Liquid bug, Roda Frog, Puku Puku, and the Vadon mob. The one I like the most is, the Puku Puku (the ones that is flying) ... really, I was shocked too look this kind of animation being possible now. I mean, mobs flying. wow! Video ... watch it in HD 720p! HD Screenshot Screens are in Full HD resolution. You can allways hit the image thumbnaill to check the images on full size, and check some details that can only be appreciated in HD resolution. *** Download link & Instructions *** If you read all the thread, you may know that this was possible thanks to the project I linked above. Doing this tests and being able to port this animated 3D is consuming me a looooot of time! As you know, I run a service were I get commisions to make maps. Affording time to do this kind of releases, it is something really hard to me. However I completely understand that making time to work for the community here is important, so as a gratitude to the people who supported our project before. Please support this release! I'm planning to add more of these free packs of this game, so as others too: world of warcraft pets? who knows!. So by posting your feedback or by adding: A comment is Greatly appreciated. A simple reputation makes me happy *A topic rating is allways a good detail from all Ensures me that this release and the project itself worthed the time of me and the team who was responsible to make this kind of features possible. Well that is all. Please stay in tune for the download link. It will be a matter of 1 of 2 days so please take a look of this thread frequently to download it. Edit: Btw: Do you think the mobs are oversized? I can make them smaller if you want... however I thought it was good to follow the idea of the "WoE guardians" which they have this size.
    1 point
  4. Original Creator: Najara Original Link: All I have done is changed over the files into Lua format. Removed treasure chests from it. Changed item numbers up to higher numbers. Once https://github.com/rathena/rathena/pull/2129 is implemented, these will work fine. I'm not giving support on this. This isn't my creation. Just providing it in lua format. Pet Tame: 35004,Custom_Monster_Tame,Custom Monster Tame,2,10000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 0; },{},{} You can change it to whatever you want but be sure to edit the lua to match it. Pet item numbers start at 50000 Download Here: pets.rar
    1 point
  5. getinventorylist; for(.@i = 0; .@i < @inventorylist_count; .@i++) { for (.@r = 1; .@r <= 5; .@r++) { .@random_bonus_id_array[.@r] = getd("inventorylist_option_id"+.@r+"["+.@i+"]"); .@random_bonus_value_array[.@r] = getd("inventorylist_option_value"+.@r+"["+.@i+"]"); .@random_bonus_param_array[.@r] = getd("inventorylist_option_parameter"+.@r+"["+.@i+"]"); } if (!@inventorylist_identify[.@i]) { delitem3 @inventorylist_id[.@i], 1, 0, @inventorylist_refine[.@i], @inventorylist_attribute[.@i], @inventorylist_card1[.@i], @inventorylist_card2[.@i], @inventorylist_card3[.@i], @inventorylist_card4[.@i], .@random_bonus_id_array, .@random_bonus_value_array, .@random_bonus_param_array; getitem3 @inventorylist_id[.@i], 1, 1, @inventorylist_refine[.@i], @inventorylist_attribute[.@i], @inventorylist_card1[.@i], @inventorylist_card2[.@i], @inventorylist_card3[.@i], @inventorylist_card4[.@i], .@random_bonus_id_array, .@random_bonus_value_array, .@random_bonus_param_array; .@count++; } } if (.@count) dispbottom .@count +" items identified."; you can try like this.... you should avoid any tricks that using atcommands. Imagine if you keep a log for every single usage of atcommands in your server, your server gonna overflooded with unnecessary logs.
    1 point
  6. Version 2.2.0

    37166 downloads

    Third Job Costumes + New Classes The Correction With the advent of jRO releasing new Job Costumes, and also, the new classes from the Taekwon branch, many of server owners want to replace the vanilla sprites or even, implement the bodystyle system. But, there's a catch! Originally jRO, and now, even kRO spriters, have made it completely off of the default pattern of palette. In a classic example, you can notice the pattern of the RO palettes. What matters is the position of the colours, as an example, for all jobs, the white-ish tones will be always on the same row, so we can use it to create custom palettes. See how it works: But jRO didn't follow the classic pattern, making it incompatible with custom palettes (@Kamishi ones included). So, I edited frame by frame of each job sprite, of each gender, mounted or not, correcting them, converting them in a way so many of the previously created palettes will work. This package includes: Alternate Outfits: Alternate Royal Guard M/F + Gryffon Battlemount + Lion Mount Alternate Ranger M/F + Warg Battlemount + Ostrich Mount Alternate Minstrel/Wanderer + Ostrich Mount Alternate ArchBishop M/F + Alpaca Mount Alternate Warlock M/F + Fox Mount Alternate Mechanic M/F + Savage Mount Alternate Genetic M/F + Savage Mount Alternate Guillotine Cross M/F + Hyena Mount Alternate Shadow Chaser M/F + Hyena Mount Alternate Sorcerer M/F + Fox Mount Alternate Sura M/F + Alpaca Mount Alternate Rune Knight M/F + Dragon Battlemount + Lion Mount New Classes Star Emperor M/F + Wolf Mount Soul Reaper M/F + Wolf Mount As requested by @Emistry, I also added an extra, making it more compatible to default palettes: Kagerou/Oboro + Frog Mount Following the another @Emistry's request, all files are now already on GRFs. The previous version had no Cashmount palette included, this one fixes the issue. Only the already released costumes are supported at this moment. The Rune Knight seems to be the last of them, it's over a year from the first release! As a final part of the package, I'm including Classic Palettes for all Alternate Costumes. Enjoy the final product!
    Free
    1 point
  7. On the Internet it is impossible to find a description of the format of this file type, namely Gravity Patch File. In developing KPatcher I gathered enough information that you could share it with the community. To simplify the writing and understanding of the text, we introduce a small definition for all GRF/GPF files and we will call them shortly - container. Version of the containers differ only by the methods encrypt the content. In his description, I will talk only about 0x200 version container. The description also is present code in C/C++ examples. So let's begin. To start analyze a simplified structure of the container: 1) Cap the container in which to store the number of files in a container, a compressed file table address container, the container version and a bit of official information; 2) The table container file contains the file name, file size, the compressed file size, compressed file size is aligned, the file position in the container and the attributes of a file in a container; 3) Compressed files. All this can be described as structures of the C/C++ To cap structure is as follows: struct grf_header { char Magic [16]; /// "Master of Magic" +\0 char Key [14]; /​​// 0x01 -&gt; 0x0E, or 0x00 -&gt; 0x00 (no encryption) uint32_t FileTableOffset; /// The location of the file table uint32_t Seed; /// What is the value of randomly uint32_t FilesCount; /// The actual number of files = FilesCount - Seed - 7 uint32_t Version; /// GRF file version: 0x102, 0x103, 0x200 }; We analyze this structure in more detail: 1) Magic [16] - an identifier that indicates the program running with a container that is in front of her GRF/GPF container, the keyword "Master of Magic"; 2) Key [14] - a key that tells what the data inside the container encryption, obsolete value is not used; 3) FileTableOffset - well, everything is clear, there is stored the offset location of the file table, I want to see that all the specified offset is not the beginning of the file, and the end cap of the container which is equal to 'sizeof (grf_header)' or 46; 4) Seed - a value that randomly invented by Koreans do not know why, probably used in conjunction with Key [14] in earlier versions of the container to protect the information inside the container, which is obsolete value is always 0; 5) FilesCount - the number of files in the container, this value is not absolute, but a bit distorted. The actual value can be obtained by doing a simple mathematical operation RealFilesCount = FilesCount - Seed - 7; 6) Version - this is how it was not hard to guess, the version container. Now, using this knowledge, try to read this information from any arbitrary container. To do this, I will use the programming language C/C++ #include <...> #include <...> #include <...> # Pragma pack (push, 1) /// Align in-memory structure of 1 byte struct grf_header { char Magic [16]; /// "Master of Magic" +\0 char Key [14]; /// 0x01 -&gt; 0x0E, or 0x00 -&gt; 0x00 (no encryption) uint32_t FileTableOffset; /// The location of the file table uint32_t Seed; /// What is the value of randomly uint32_t FilesCount; /// The actual number of files = FilesCount - Seed - 7 uint32_t Version; /// GRF file version: 0x102, 0x103, 0x200 }; # Pragma pack (pop) # Define GRF_HEADER "Master of Magic" # Define GRF_HEADER_SIZE 46 int main () { FILE * FD = NULL; struct grf_header Header = {0}; uint32_t RealFilesCount = 0; FD = fopen ("data.grf", "rb"); /// Read the header container fread (&amp; Header, GRF_HEADER_SIZE, 1, FD); /// Check if this is a GRF/GPF container or not if (strncmp (Header.Magic, GRF_HEADER, 16) { return 0; } /// Now the structure is stored Header informations about current container /// And can easily access them /// The variable is now RealFilesCount the actual number of files in a container /// On this can start reading the information about files RealFilesCount = Header.FilesCount - Header.Seed - 7; return 0; } In this example, I make out the structure of GRF/GPF files and shows how to use the C/C++, you can determine that this is the GRF/GPF file, which version of the file and how many files are contained in this container. And so, to deal with the basic description of the container and having considered the example of obtaining information about the container down to work with the data container. The first thing to get a table with data in the file container. Fully describe the entire structure of the table files can be very simple: table: [<zsize>. l <size>. l [<fname>. s <fentry> .17 b] *] fentry: [<zsize>. l <zsizeal>. l <size>. l <flags>. b <offset>. l] .17 b From this simple circuit structure is visible to full data is located on the very structure of the file table and file table With this information, can easily get information about all files stored in the container. Table with a container files can also be described as a structure: struct grf_fentry { uint32_t zSize; /// Size of packed data uint32_t zSizeAl; /// The same thing only with alignment uint32_t Size; /// Size of uncompressed data uint8_t Flags; /// Flag file (GRF_FLAG_FILE, GRF_FLAG_MIXCRYPT, GRF_FLAG_DES) uint32_t Offset; /// offset into the GRF file (starts immediately after grf_header) }; Describe in detail the structure, I will not, in the comments should explain everything quite clear. #include <...> #include <...> #include <...> .................................................. ................. int main () { .................................................. ......... uint8_t * pBuffer = NULL, * pZBuffer = NULL; uint32_t TableSize = 0, zTableSize = 0; /// Move the file pointer at the beginning of the file table fseek (FD, FileTableOffset + GRF_HEADER_SIZE, SEEK_SET); /// Read compressed and the actual size of the MFT if (! fread (&amp; zTableSize, 4, 1, FD) | |! fread (&amp; TableSize, 4, 1, FD)) { return 0; } /// Allocate the necessary memory volume and read the file table pBuffer = new uint8_t [TableSize]; pZBuffer = new uint8_t [zTableSize]; if (! fread (pZBuffer, zTableSize, 1, FD)) { delete [] pBuffer, delete [] pZBuffer; return 0; } /// Extract the file table /// If you want to use the code presented here will have to connect the library zlib /// This function is part of GrfLib for KPatcher /// The variable pBuffer now stored unpacked and ready to read the file table if (zio:: zlib_uncompress (pBuffer, TableSize, pZBuffer, zTableSize)! = TableSize) { delete [] pBuffer, delete [] pZBuffer; return 0; } delete [] pZBuffer; return 0; } We now have a fully ready to read the file table. Now it remains the case for small, properly read and write to it, we will write to the memory of which optionally can be written to a file. For that would work with the data it was convenient to define another structure that will remind you what struct grf_fentry, but will carry more useful information: struct _FileNode { std:: string FileName; /// File Name uint32_t NameHash; /// Hash the file name uint32_t FileOffset; /// file offset in a container uint32_t FileSize; /// Size uint32_t zFileSize; /// compressed file size uint32_t zFileSizeAl; /// compressed file size aligned uint8_t FileFlags; /// Flags file int32_t Cycle; /// Cycle (used for encrypted files) }; This structure can sozherzhat information about only one file, and must keep information about all files, but it requires some realties store, which will be convenient to work: typedef std:: list &lt;_FileNode&gt; _FilesList; Now that is all that is necessary, we can begin reading the information about files #include <...> #include <...> #include <...> .................................................. ................. .................................................. ................. struct grf_fentry { uint32_t zSize; /// Size of packed data uint32_t zSizeAl; /// The same thing only with alignment uint32_t Size; /// Size of uncompressed data uint8_t Flags; /// Flag file (GRF_FLAG_FILE, GRF_FLAG_MIXCRYPT, GRF_FLAG_DES) uint32_t Offset; /// offset into the GRF file (starts immediately after grf_header) }; # Define GRF_TABLE_SIZE 17 # Define GRF_FLAG_FILE a # Define GRF_FLAG_MIXCRYPT 2 # Define GRF_FLAG_DES 4 struct _FileNode { std:: string FileName; /// File Name uint32_t NameHash; /// Hash the file name uint32_t FileOffset; /// file offset in a container uint32_t FileSize; /// Size uint32_t zFileSize; /// compressed file size uint32_t zFileSizeAl; /// compressed file size aligned uint8_t FileFlags; /// Flags file int32_t Cycle; /// Cycle (used for encrypted files) }; typedef std:: list &lt;_FileNode&gt; _FilesList; int main () { .................................................. ......... .................................................. ......... _FilesList FilesList; for (uint32_t Offset = 0; Offset <tablesize;) {="" get="" the="" file="" name="" length="" size_t="" fn_size="strlen" ((char="" *)="" (pbuffer="" +="" offset));="" if="" (fn_size=""> = 0x100) { delete [] pBuffer; return 0; } grf_file_table FileEntry = {0}; /// Get a pointer to the file name char * FileName = (char *) (pBuffer + Offset); Offset + = FN_Size + 1; /// Get the file information memcpy (&amp; FileEntry, (pBuffer + Offset), GRF_TABLE_SIZE); Offset + = GRF_TABLE_SIZE; /// Skip the directories and files whose size is equal to 0 if (! (FileEntry.Flags &amp; GRF_FLAG_FILE) | | FileEntry.Size == 0) continue; /// Fill the structure with the file information _FileNode Node; Node.FileName.append (FileName, FN_Size); Node.FileFlags = FileEntry.Flags; Node.NameHash = zio:: zlib_crc32 (FileName, FN_Size); Node.FileOffset = FileEntry.Offset; Node.FileSize = FileEntry.Size; Node.zFileSize = FileEntry.zSize; Node.zFileSizeAl = FileEntry.zSizeAl; Node.Cycle = -1; /// Get the information needed to decrypt the file if (Node.FileFlags &amp; GRF_FLAG_MIXCRYPT) { Node.Cycle = 1; for (uint32_t i = 10; Node.zFileSize&gt; = i; i = i * 10) Node.Cycle + +; } if (Node.FileFlags &amp; GRF_FLAG_DES) Node.Cycle = 0; /// Add all the information on file in the repository. FilesList.push_back (Node); } return 0; } Now, the variable contains FilesList informations about each file in the container and can easily burn any data to a file. Now we can unite all that is written above together and we get: #include <stdio.h> #include <string.h> #include <string> #include <list> #include <stdint.h> #include <zlib.h> using namespace std; #pragma pack(push, 1) /// Align in-memory structure of 1 byte struct grf_header { char Magic[16]; /// "Master of Magic" +\0 char Key[14]; /// 0x01 -> 0x0E, or 0x00 -> 0x00 (no encryption) uint32_t FileTableOffset; /// The location of the file table uint32_t Seed; /// What is the value of randomly uint32_t FilesCount; /// The actual number of files = FilesCount - Seed - 7 uint32_t Version; /// GRF file version: 0x102, 0x103, 0x200 }; #pragma pack(pop) #define GRF_HEADER "Master of Magic" #define GRF_HEADER_SIZE 46 #pragma pack(push, 1) /// Align in-memory structure of 1 byte struct grf_fentry { uint32_t zSize; /// Size of packed data uint32_t zSizeAl; /// The same thing only with alignment uint32_t Size; /// Size of uncompressed data uint8_t Flags; /// Flag file (GRF_FLAG_FILE, GRF_FLAG_MIXCRYPT, GRF_FLAG_DES) uint32_t Offset; /// offset into the GRF file (starts immediately after grf_header) }; #pragma pack(pop) #define GRF_TABLE_SIZE 17 #define GRF_FLAG_FILE 1 #define GRF_FLAG_MIXCRYPT 2 #define GRF_FLAG_DES 4 struct _FileNode { std::string FileName; /// File Name uint32_t NameHash; /// Hash the file name uint32_t FileOffset; /// file offset in a container uint32_t FileSize; /// Size uint32_t zFileSize; /// compressed file size uint32_t zFileSizeAl; /// compressed file size aligned uint8_t FileFlags; /// Flags file int32_t Cycle; /// Cycle (used for encrypted files) }; typedef std::list <_FileNode> _FilesList; int main() { /// Some declarations FILE *FD = NULL; struct grf_header Header; uint32_t RealFilesCount = 0; uint8_t * pBuffer = NULL, * pZBuffer = NULL; uint32_t TableSize = 0, zTableSize = 0; _FilesList FilesList; FD = fopen("naoro.grf", "rb"); fread(&Header, GRF_HEADER_SIZE, 1, FD); if ( strncmp(Header.Magic, GRF_HEADER, 16) ) return 0; /// Now the structure is stored Header informations about current container /// And can easily access them /// The variable is now RealFilesCount the actual number of files in a container /// On this can start reading the information about files RealFilesCount = Header.FilesCount - Header.Seed - 7; /// Move the file pointer at the beginning of the file table fseek(FD, Header.FileTableOffset + GRF_HEADER_SIZE, SEEK_SET); /// Read compressed and the actual size of the MFT if ( !fread (&zTableSize, 4, 1, FD) || !fread (&TableSize, 4, 1, FD) ) { return 0; } /// Allocate the necessary memory volume and read the file table pBuffer = new uint8_t [TableSize]; pZBuffer = new uint8_t [zTableSize]; if( !fread (pZBuffer, zTableSize, 1, FD) ) { delete [] pBuffer, delete [] pZBuffer; return 0; } fclose(FD); /// Extract the file table /// If you want to use the code presented here will have to connect the library zlib /// This function is part of GrfLib for KPatcher /// The variable pBuffer now stored unpacked and ready to read the file table if ( uncompress((Bytef*)pBuffer, (uLongf*)&TableSize, (Bytef*)pZBuffer, zTableSize) != Z_OK ) { delete [] pBuffer, delete [] pZBuffer; return 0; } delete [] pZBuffer; for ( uint32_t Offset = 0; Offset < TableSize; ) { size_t FN_Size = strlen((char*)(pBuffer+Offset)); if ( FN_Size >= 0x100 ) { delete[] pBuffer; return 0; } grf_fentry FileEntry = {0}; /// Get a pointer to the file name char *FileName = (char*)(pBuffer+Offset); Offset += FN_Size + 1; /// Get the file information memcpy(&FileEntry, (pBuffer+Offset), GRF_TABLE_SIZE); Offset += GRF_TABLE_SIZE; /// Skip the directories and files whose size is equal to 0 if ( !(FileEntry.Flags&GRF_FLAG_FILE) || FileEntry.Size == 0 ) continue; /// Fill the structure with the file information _FileNode Node; Node.FileName.append(FileName, FN_Size); Node.FileFlags = FileEntry.Flags; Node.NameHash = crc32(0, (Bytef*)FileName, FN_Size); Node.FileOffset = FileEntry.Offset; Node.FileSize = FileEntry.Size; Node.zFileSize = FileEntry.zSize; Node.zFileSizeAl = FileEntry.zSizeAl; Node.Cycle = -1; /// Get the information needed to decrypt the file if ( Node.FileFlags&GRF_FLAG_MIXCRYPT ) { Node.Cycle = 1; for( uint32_t i = 10; Node.zFileSize >= i; i = i*10 ) Node.Cycle++; } if ( Node.FileFlags&GRF_FLAG_DES ) { Node.Cycle = 0; } /// Add all the information on file in the repository. FilesList.push_back(Node); } delete[] pBuffer; /// Creating empty file FD = fopen("files_list.txt", "w+"); _FilesList::iterator itr = FilesList.begin(); _FilesList::iterator itr_end = FilesList.end(); /// Fill the newly created file data. fprintf(FD, "FileName - FileSize - FilePos\n"); for ( ; itr != itr_end; itr++) fprintf(FD, "%s - %d - %d\n", itr->FileName.c_str(), itr->FileSize, itr->FileOffset+GRF_HEADER_SIZE); fclose(FD); return 0; } Fully working source code that reads the GRF/GPF file and prints the contents a file. main.rar
    1 point
  8. b]68430[/b] change this to your desired emperium HP
    1 point
×
×
  • Create New...