Encrypting and Decrypting

talk and review codes here

Moderators: Q-dad~TAG, EXP STAFF, Moderator

Postby Eagle Eye » 10-02-2007 11:38 PM

Thought I'd try this Delphi 6. but you can no longer get a key..

They have updraged to a newer version..

I don't really want to download it..LOL..

Anyone have a set of keys I can use?

EE
Image
User avatar
Eagle Eye
Moderator
 
Posts: 164
Joined: 02-11-2004 08:40 PM

Postby Fred » 10-03-2007 05:19 AM

Link in your PM.
Tons of Software
No Talent
Fred
MOD Scientist
 
Posts: 113
Joined: 06-29-2004 05:41 AM

Postby MichaBen » 12-09-2008 07:22 AM

It's an old topic, but I was looking for the decryption key for some time and found the assembler code here. Rather then using the assembler code, I decided to translate it to C++. In case there are more people wondering what the code actually does, I decided to explain it here:

Code: Select all
  // First of all, check if the file is encoded at all, for this check the
  // header (first 4 bytes), when not decoded simply exit, and the text can used.
  mov eax,pMemory
  cmp dword ptr [eax],01524353h
  je @srcdec
  jmp @exit

  // We now know the file is encoded, so we start decoding it. First of
  // all, invert the text, the encoded text is stored back to front.
  @srcdec:
 
  // First of all, we store the filesize (minus header) in the eax (don't ask
  // me for what reason, as this seems to be not used).
  mov eax,FileSizeU
  sub eax,4h
 
  // In 3di, we store the pointer to the last byte in the data
  mov edi,pMemory
  add edi,FileSizeU
  sub edi,01h
 
  // Inside ecx, we store the number of bytes we have to swap. Since the
  // bytes are swapped, 2 bytes are put in the correct position with 1 call. So
  // we only need to handle half of the bytes, so right shift ecx 1 bit and subtract 2
  mov ecx,FileSizeU
  shr ecx,1
  sub ecx,2
 
  // Finally in esi we store the pointer of the first byte after the header
  mov esi,pMemory
  add esi,04h
 
  // Now the main loop
  @loc_004D74B5:
 
  // What this code does is simply flip the bytes at the current pointer of esi and
  // edi. As shown above, esi contains starts as pointer to the first byte, while edi
  // as pointer to the last byte. So we put 2 bytes in the correct position here
  mov al, byte ptr [esi]
  mov bl, byte ptr [edi]
  mov byte ptr [esi], bl
  mov byte ptr [edi], al
 
  // Go to the next byte, increase esi and lower edi.
  inc esi
  dec edi
 
  // Lower the bytes left counter ecx by 1, when > 0 we have bytes left to invert, so continue
  dec ecx
  jne @loc_004D74B5

  // Now the bytes are in the correct order, start with decoding. First of all, the registers are
  // set: esi will contain a pointer to the first byte of the encoded data, edi contains the key
  // and ecx contains the number of bytes to decode.
  mov esi,pMemory
  add esi,04h
  mov edi,2A5A8EADh
  mov ecx,FileSizeU
  sub ecx,04h
 
  // Here the actual loop starts to decode the text. Unlike for inverting, this loop
  // is repeated for each byte, as we decode 1 character at a time.
  @loc_004D74CB:
 
  // This is the actual decoding. The decoding is done by manipulating the key each
  // byte. We store the key in eax for now in order to manipulate it. First we rotate
  // the key 11 bits to the left (rol function). Then we add the original key again,
  // and rotate the result again 4 bits to the left. Finally we XOR the key with 1, and
  // store the key in the eax register again, so for the next byte we continue with
  // the new key.
  mov eax, edi
  rol eax, 0Bh
  add eax, edi
  rol eax, 04h
  xor eax, 00000001h
  mov edi, eax
 
  // Now the key has been made, simply xor the current byte with the lowest 8 bits of
  // the key (al = lower 8 bits of eax)
  mov bl, byte ptr [esi]
  xor bl, al
  mov byte ptr [esi], bl
 
  // Increase the pointer by 1 to go to the next byte and lower bytes left to do by 1. When
  // ecx > 0, jump to @loc_004D74CB for next byte
  inc esi
  dec ecx
  jne @loc_004D74CB
 
  // When ecx is 0, jne will be ignored and we end up here. Subtract the filesize by 4 and increase
  // the pointer by 4 to remove the first 4 bytes (header) and it's done.
  add pMemory,4
  sub FileSizeU,4
  @exit:


In C++, decoding (after inverting the bytes) will look like this:

Code: Select all
    uint32_t key     = 0x2A5A8EAD;
    size_t   pointer = 0;

    // Decrypt
    while (pointer < dataSize) {
        // Update the key
        uint32_t key2;
        key2  = (key  << 11) | (key  >> 21); // Rotate 11 bits to left
        key2 += key;                         // Add original key
        key2  = (key2 <<  4) | (key2 >> 28); // Rotate 4 bits to left
        key2 ^= 1;                           // XOR 1
        key   = key2;

        // XOR byte with lowest 8 bits of key
        data[pointer] ^= (key & 0xff);

        // Continue with next byte
        pointer++;
    }


I haven't looked at encrypting yet, but it's probably the same in invert order (first XOR the text, then invert byte order). Since XOR is symmetric, manipulating the key should be the same code.
MichaBen
Junior Member
 
Posts: 5
Joined: 12-03-2008 12:12 PM

Postby devilsclaw » 12-16-2008 10:02 PM

I know your probably using a C++ compiler to compile that but its C code not C++.

C++ in general is using object oriented code. and the other main diff is that in C++ you can do for(int i = 0; i < 100; ++i){}

where in C standard 99 not 98 you have to pre define the variable.

int i;
for(i = 0; i < 100; ++i){}

if you wanted to make that into C++ you would have to change it into an object.

Code: Select all
class BHDDEC
{
   void decrypt(char* buffer,unsigned int key){}
};

int main()
{
   BHDDEC bhd;
   bhd.decrypt(buffer,key);
}

that would be an example of C++ and not C.

If people want I can show them how I did it in C as well its similar but slightly more structured.
User avatar
devilsclaw
Administrator
 
Posts: 42
Joined: 08-06-2004 10:46 PM

Postby MichaBen » 12-17-2008 02:03 PM

And how can you see from that code that it's C and not C++? It's obviously only part of the code (else there would have been a main function). It's actually a special Stream class, allowing you to read encrypted files the same way as any other file. So with the classes I have you can create a Stream in multiple ways, for example:

Code: Select all
// Create stream from encrypted file
Stream *scr = new SCRStream( "items.def" );
// Create stream from normal file
Stream *txt = new FileStream( "items.txt" );


Or you can even read files directly from the game, in this case Escalation PFF file:
Code: Select all
Resource *res = new Resource( "E:\\Joint Operations", "jox01" );
Stream *file = res->openFile( "items.def" );


Which can then of course be simply decrypted using:
Code: Select all
Stream *file2 = new SCRStream( file );


So no matter if it's from the disk, from memory, from PFF or a decrypted scr, you can always read data from it this way:
Code: Select all
stream->read( &version, 4, 1 );
stream->seek( 3, SEEK_CUR );
std::string name = stream->gets();


Or simply feed the stream to another class:
Code: Select all
BINFile *bin = new BINFile( stream1 );
Object3DI *graphic = new Object3DI( stream2 );
Mission *mission = new Mission();
mission->loadNpz( stream3 );
mission->convertNpjToMis( resource );
mission->saveMis( "test.mis" );


So the code in a whole is object orientated.
MichaBen
Junior Member
 
Posts: 5
Joined: 12-03-2008 12:12 PM

Postby devilsclaw » 12-22-2008 02:24 PM

For one the code you originally posted is C period.

Code: Select all
    uint32_t key     = 0x2A5A8EAD;
    size_t   pointer = 0;

    // Decrypt
    while (pointer < dataSize) {
        // Update the key
        uint32_t key2;
        key2  = (key  <<11>> 21); // Rotate 11 bits to left
        key2 += key;                         // Add original key
        key2  = (key2 <<4>> 28); // Rotate 4 bits to left
        key2 ^= 1;                           // XOR 1
        key   = key2;

        // XOR byte with lowest 8 bits of key
        data[pointer] ^= (key & 0xff);

        // Continue with next byte
        pointer++;
    }


This is the only thing you showed and it is only C not C++ you didn't show anything that would even suggest C++.

the second code you show is just showing that your able to interface into C++ code that someone else created it also does not show you know how to even code in C++.

sure since you interfaced into some of the C++ stdlib it means your code is not longer C compatible but it still retain the original code you posted is C not C++.

here is a simple example of how to make that C++

Code: Select all
template<typename>
    T rol ( T input,int pos ) //bit wise role to the left since c++ does not have one
{
  return ( input<<pos>> ( ( CHAR_BIT*sizeof ( T ) )-pos ) & ( ~ ( T ( -1 ) << pos ) ) );
}

    uint32_t key     = 0x2A5A8EAD;
    size_t   pointer = 0;

    // Decrypt
    while (pointer < dataSize) {
        // Update the key
        uint32_t key2;
        key2  =  rol(key,11);  // Rotate 11 bits to left
        key2 += key;             // Add original key
        key2  =  rol(key,4);    // Rotate 4 bits to left
        key2 ^= 1;                // XOR 1
        key   = key2;

        // XOR byte with lowest 8 bits of key
        data[pointer] ^= (key & 0xff);

        // Continue with next byte
        pointer++;
    }


yes there is a fine difference but one is C only code and the other is C++,
User avatar
devilsclaw
Administrator
 
Posts: 42
Joined: 08-06-2004 10:46 PM

Postby MichaBen » 12-23-2008 11:30 AM

I think adding 3 lines of pretty ugly code to a program just to make a very tiny piece of the code C++ rather then C is pretty pointless :wink: Does this mean that if I posted 1 more line of the example code (the part where it says data = new uint8_t[dataSize]; ) here it would have been C++ and not C? Then this discussion would be even more pointless.

As for "being able to interface into C++ code that someone else created", the C++ code is not create by someone else, I wrote the C++ code myself. But anyway, I'm not going to bother to discuss this further, I have a computer game development project with a deadline where I still have to code a big part of the AI for so I have better things to do then pointless discussing about if a tiny piece of a whole source code if C or C++ with somebody who didn't see the rest of it.
MichaBen
Junior Member
 
Posts: 5
Joined: 12-03-2008 12:12 PM

Postby devilsclaw » 12-23-2008 11:25 PM

Code: Select all
template<typename T>
    T rol ( T input,int pos ) //bit wise role to the left since c++ does not have one
{
  return ( input<<pos ) | ( input >> ( ( CHAR_BIT*sizeof ( T ) )-pos ) & ( ~ ( T ( -1 ) << pos ) ) );
}


Its ugly true. but there is a reason for it, and if you knew what it even did you would not complain.

first of all you code is limited to only dealing with INT values. for a specific purpose and totally not reusable.

templates allow you to pass any set of data types you want and it will handle it accordingly if you code it correctly. the code above works with all data types except I would not use it on anything like floats or double since that would not be a smart thing to do. and it also does some clean up work that your code does not that could cause some problems if you ever tried to reuse any of it in something more complex.

also for the fact that you cant even realize when your interfacing and actually coding your own code means you don't know much about programming.

Just because some of your code calls on the stdlib using iostream and using fstream to read and write some data does not mean you coded the actually object oriented section of your code your just interfacing with it.
User avatar
devilsclaw
Administrator
 
Posts: 42
Joined: 08-06-2004 10:46 PM

Postby MichaBen » 12-24-2008 05:34 AM

Well as I already said, I have better and more important things to do then having useless discussions with people that have no idea where they are talking about. But if you want to be a smartass, go for it. You will only ruin it for other people who might come here for useful information, as people won't be excited about posting code that might help others if they can end up in a useless discussion with somebody that doesn't know where he is talking about.
MichaBen
Junior Member
 
Posts: 5
Joined: 12-03-2008 12:12 PM

Postby devilsclaw » 12-24-2008 08:34 PM

fine you want to learn something useful

lets say you want to code this for speed
uint32_t key2; should be outside of the while loop because the local value is destroyed every loop and reallocated slowing down the program if you want it clears you can always reinitialize it to 0 or have a program that directly assigns the value to it.

if you want your program to be faster you would use pre increment instead of post increment since if you use post it will have to copy the original value add it and then assign it back to memory were pre increment will just assign the value directly to the memory location.

also this job is better suited with a for loop since its designed specifically for this type of task but that is just symantics

Code: Select all
    uint32_t key     = 0x2A5A8EAD;
    uint32_t key2; //Keep it outside of the loop for speed and memory allocation
   
     for(size_t pointer = 0;pointer < dataSize; ++pointer) {
        // Update the key
        key2  = (key  << 11) | (key  >> 21); // Rotate 11 bits to left
        key2 += key;                         // Add original key
        key2  = (key2 <<  4) | (key2 >> 28); // Rotate 4 bits to left
        key2 ^= 1;                           // XOR 1
        key   = key2;

        // XOR byte with lowest 8 bits of key
        data[pointer] ^= (key & 0xff);
    }


if your going to use pointer else were or your going to do another for loop its faster to leave pointer out side of the for loop.
User avatar
devilsclaw
Administrator
 
Posts: 42
Joined: 08-06-2004 10:46 PM

Postby MichaBen » 12-25-2008 05:56 AM

To bad, pointer++ and ++pointer compile into the same code, and so does moving the definition of key2 in or outside the loop. Having pre or post increment only matters when you use it on a class that has this operator overloaded. And the reason why I used a for loop was that I simply translated the asm code and did not bother about that. The for and while loop compiile into the same code after all, so after translating I ended up with a while loop that I never bothered to change after rewriting a small part of the code.

But anyway, since you don't know where you are talking about, maybe it's better to stop with this pointless discussion. First you thought, without seeing the whole code, that you knew how I implemented it, and you got it wrong. Then you thought you knew my knowledge level of coding without seeing any further code, and now you suddenly think that I came here to learn useful about optimizing code, yet your example compiles into exactly the same code (ok, it might speed up the compiler 1 nanosecond). I just posted the code in case somebody else would find it useful. I know there are more people interested in decrypting items.def or other encrypted files for modding/mapping tools, but not everybody can read assembler and know what was written in that code.
MichaBen
Junior Member
 
Posts: 5
Joined: 12-03-2008 12:12 PM

Postby BuLL » 12-25-2008 11:07 AM

What`s the code for knocking two daft buggers head`s together? :D
ps...I`m in need of a fully unlocked bhdmed for the NSO-mod mappers.....
Any ideas on if it`s possible guy`s?...Cheers & merry xmas :wink:
BuLL
Professional "Pie-Eater"
 
Posts: 226
Joined: 07-29-2005 11:27 AM
Location: GB

Postby Q-dad~TAG » 12-25-2008 07:50 PM

BuLL wrote:What`s the code for knocking two daft buggers head`s together? :D

Need to specify...: C or C++ :lol:
TXP (Terrain Xpansion Pack) for DF2: http://txp.df2.org/

Image
User avatar
Q-dad~TAG
Senior Member
 
Posts: 269
Joined: 03-29-2004 01:00 AM

Postby BuLL » 12-27-2008 08:44 PM

BuLL wrote:ps...I`m in need of a fully unlocked bhdmed for the NSO-mod mappers.....
Any ideas on if it`s possible guy`s?...Cheers & merry xmas :wink:


Hmm..No takers then eh?...Never mind,thought as much.
Image

I`m only overweight because of a "feet disorder"...I can`t keep them out of the f*cking Pantry.
BuLL
Professional "Pie-Eater"
 
Posts: 226
Joined: 07-29-2005 11:27 AM
Location: GB

Postby JoeMama » 12-31-2008 05:09 PM

BuLL wrote:
BuLL wrote:ps...I`m in need of a fully unlocked bhdmed for the NSO-mod mappers.....
Any ideas on if it`s possible guy`s?...Cheers & merry xmas :wink:


Hmm..No takers then eh?...Never mind,thought as much.


Google it man there are multiple hits. But i didn't actually look into them to see how much was unlocked in each.
3D Studio Max 8
Modeling Since 2001(I think O_o)
"Rehab Is For Quitters"
JoeMama
Lost in Time
 
Posts: 68
Joined: 03-27-2004 07:22 PM

PreviousNext

Return to Coders Hell

Who is online

Users browsing this forum: No registered users and 0 guests

cron