6 Replies Latest reply on Apr 4, 2007 7:03 PM by SunghyunWang_(bruce)

    [Tip] How to protect Image file


      If you have ever wanted to protect your image file, especially within your Flash content,
      this article will be helpful.

      First of all, there are some points you need to protect when you deliver image data with Flash.

      1. Internet Browser Cache.

      Even though you use 'HTTPS' protocol when you deliver your file,
      if it is pass the 'Network (or Protocol) Layer' of your machine, it is already in 'plain' data
      (not encrypted), and can be read by Internet Browser.
      Those 'plain' data will be stored in Internet Browser's Cache directory.

      There are many Internet Browser Cache reader programs, and they can intercept those
      data before the Internet Browser program deletes the cache files.

      So, just using 'HTTPS' is not an answer. You need to encode your image data
      with your own (or with well known cypher algorithms) encoding/decoding methods.

      In this article, I want to explain more detail about this. I scramble the image
      so that make it hard to figure out what the original image was, not only with human eyes
      but also with 'strong enough' 'Key' length.

      2. Screen Capture.

      Even if you encoded your image data, it will be finally shown on your screen,
      without any noises, or any other ugly filters.
      So, you can 'Capture' your monitor screen itself.

      There can be many ways to avoid this. First, you can erase the system's 'Clip board'.
      You just can erase it regularly, or you can detect whether the Internet Browser -which is
      showing your image data- is active or not and erase clip board when it is active (in foreground),
      and hide your Flash area when the browser is inactive (in background).

      If a hacker just take a picture of monitor screen with high quality Camera,
      you still can avoid that, by showing some black rectangle, or any layers on the screen
      regularly only in very short period (like mili-second). But I think this way sometimes you feel
      tired or be annoyed when you watch that kind of blinking screen.

      == About my code ==

      What I want to present here today is 'modifying(encoding) the image' data itself.
      There are many ways you can try for modifying your image data and revert it back to original data.

      You can use legacy block cipher algorithms like DES, AES, for encoding and decoding the
      image data, because the image data (RGB values) what Flash uses is actually a combination of 'bit's.
      But if you decode the 'encoded image' data, you probably use 'get pixel'/'set pixel' function for
      reconstructing the proper 'RGB' value of each pixel. But I am sorry that this function is extremely slow
      so that you need to wait for a couple of minutes to see an image.

      So, what I want to show you today is 'Scrambling the image' like 'picture puzzle',
      with using 'copyPixels' function which is 'extremely fast'.
      (Actually, there can be many other solutions for this, so please don't hesitate to proceed your own research)

      Let's say you have 8*8 pixel size of image blocks, and you completely disorder those blocks for
      entire image area. That size of block is too small to figure out where it should be, with our
      humble human being's naked eyes. So, you need to know the 'answer', which is saying what image block
      was originally on which 'cell'. This 'answer' is the 'key' for my simple 'image scramble' logic.
      The 'key' I said here, you should understand that, is the 'key' value of normal 'block cipher' algorithms.

      So, if you know the key, you can rearrange all those 'blocks' back, but if you don't know the key,
      simply you can't do that, or you need to wates tremendous time for that.

      Here, I use 16*16 size block for your eye's convenience, and with 8*8 size of 'matrix' which is
      comprised of each 16*16 size blocks. I mean, one 8*8 matrix has 64 blocks, so each block of
      one 'matrix' can be at '1st cell of matrix or 64th cell of matrix. So, the 'odds' is 'Factorial of 64',
      which is 64! == 1.268869322e+89 .

      Let's say you know my algorithm (complete source code), and you try every different 'matrix' values.
      If it takes 0.001 seconds to test one 'matrix' value you have chosen, it will take
      "(64!) / (1000*60*60*24*365) = 4.0235582250724303685766549129617e+78" Years!!!! to find exact matrix value.

      == FLA sample ==

      In my sample *.fla file, I embedded all those 'key' values. So, you can not use my sample directly for your
      own project. But I think this sample will give you an useful idea for your own implementation.

      <* Exchanging the key values *>

      For example, you need to get the 'key' values from the server, only when it is needed.
      You can use 'loadVariables()' function for this purpose. But, all data delivered by 'loadVariables()' or
      'getUrl()', or any other functions of Flash, are 'Cached'.... So, you need to exchange that 'key' values
      more safer way.

      One of that 'safer key exchange' is to use 'token'. For example, when the client requests the key value
      to the server, the client should generate an random value (I will call it 'token') and send it to the server.
      Now the server modifies the 'key' value 'with the token', and sends back to client. Finally, the client
      decode the 'key' value with the token value it generated.

      As you can see, my logic is just 'rearranging each blocks' with respond to the given matrix values (key).
      It is really really simple. There in the ActionScript code, you can see 3 matrix, and some other variables.

      var chessunit = 16 // Size of block
      var arrayw = 8 // Width of Matrix
      var arrayh = 8 // Height of Matrix
      var arraysize = arrayh * arrayw
      var chessarray = Array (arraysize) // Matrix for decoding
      chessarray = Array (64,37,5,35,45,25,52,38,12,61,34,23,3,26,39,58,32,28,17,2,60,16,59,19,57,48,43,18,47,21,4 0,15,31,6,44,46,30,51,27,56,20,24,13,7,42,1,49,54,36,53,9,50,4,8,10,14,33,11,22,63,55,29,4 1,62)

      // In case of the width of an image is not exactly the multiple of the width of matrix,
      // we need to encode the right most area of the image.
      // So, I simply use another matrix for only that area.
      // Maybe You can generate more bigger image, of which the width of it is exactly the multiple of
      // the width of matrix. And you let the decoder to show only the original size of the image.
      // Please try yourself. :)
      var dwArray = Array (32,19,3,18,23,13,26,6,31,17,12,2,20,29,16,14,9,1,30,8,10,24,22,11,15,28,7,4,21,25,27,5)

      // In case of the Height of an image is not exactly the multiple of the Height of matrix,
      // we need to encode the bottom most area of the image.
      // So, I simply use another matrix for only that area.
      // Maybe You can generate more bigger image, of which the Height of it is exactly the multiple of
      // the Height of matrix. And you let the decoder to show only the original size of the image.
      // Please try yourself. :)
      var dhArray = Array (40,23,4,22,29,16,33,24,8,38,21,15,2,17,37,20,18,11,1,10,12,36,30,27,13,25,28,14,19,32,35 ,7,5,26,3,31,34,6,9,39)

      You can change the block size, matrix size, any values you want.
      By the way, if the block size becomes smaller, you'll get more stronger security level. But you have to
      compensate it with the slow down of the performance.

      ** Ooops, I can not attach my sample *.fla file, but only ActionScript code here...
      But I believe you can try without testing my *.fla sample.
      If you really want to test it, please mail me. (brucewang.korea@gmail.com)

      ** You need to 'export' image object, with the name of "img0".

      == Image encoder ==

      Encoding (Scramble) the original image is also simple. You just need to copy each blocks in reverse of
      the 'ActionScript code'. That's all. You just use same 'matrix', but copy source and target reverse of
      ActionScript code. I think you can write it with any languages you like, C/C++, C#, Java, and
      anything.... right?

      == Block cipher ==

      Now, you know that my implementation is kind of 'intuitive' representation of 'block cipher'.
      More precisely, it is called 'ECB', which encodes each encoding block (matrix) with the key values
      from the beginning to the end. You can twist the matrix every time you pass one matrix area of an image.
      It is called 'chaining'. There are some 'chaining' block cipher methods like 'CBC'...
      (If you want to know more, please look up " http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation ")

      Thank you for your time to read my humble article,
      and wish you Good luck. :)

        • 1. Re: [Tip] How to protect Image file
          SunghyunWang_(bruce) Level 1
          One thing you need to know is, you should use 'lossless' image file formats (PNG, GIF, etc), not JPG in this case.

          It's because JPG is lossy, it encodes every 8*8 pixel area, so if you save the 'scrambled' image with JPG, you will lose original image quality. So, if you
          decode again with my code, you will see ugly image.

          I hope you'll understand why.

          So, the drawback of my method is, you will have somewhat bigger data size....
          • 2. Re: [Tip] How to protect Image file
            kglad Adobe Community Professional & MVP
            i don't know if anyone else appreciated your post, but i did. not that i care about protecting images. but i do have an interest in protecting actionscript code and your post contained some ideas that i could use.

            • 3. Re: [Tip] How to protect Image file
              SunghyunWang_(bruce) Level 1
              I am so glad to hear that :)

              Best regards,
              • 4. Re: [Tip] How to protect Image file
                very useful. Could you somehow use the same technique to encode actionscript, like instead of scrambling the pixels scarmble the letters in the code?
                • 5. [Tip] How to protect Image file
                  SunghyunWang_(bruce) Level 1
                  Hello Crandom,

                  If you want to encrypt a critical strings, like special server script url or parameters, then it is simple.

                  The most simple and faster method is to "XOR ing the string" with a key string. You use the same key string when you encode and decode (by Just using XOR). This is similar to 'Stream cipher' algorithms.

                  And there is "open source cipher algorithm" (called AS-CryptoLib) written in ActionScript, including most of algorithms like Hash, Block cipher, RSA... if you want more stronger encryption strength..

                  But I bet you also want to encode your script logic itself. In that case, you should write your own 'Interpreter'. For example, you encode all your ActionScript source code string, and decode it, and you interpret each script tokens like 'if' 'for' 'while', etc...

                  Actually, your question also inspired me to think about loading script string and run it on the fly.
                  Maybe.... we can start from this article...
                  " http://www.adobe.com/cfusion/knowledgebase/index.cfm?id=tn_16691"

                  I suggest you just use commercial SWF file encrypting tools like Ameyata's "SWF encrypt". It changes the SWF file structure so that usual 'SWF file decompilers' can not read codes properly.

                  And.... If you can use Flex2 (for your current project), and it is ok with you (If you don't need to change a lot in your current project) to use JavaScript to control your objects or behavior of SWF file, then I think there is another possible way.
                  After you decode the Javascript string, you load a web page, or change the content of HTML file already opened, so that your new script will be working, as what you wanted to be. But I didn't test it :)

                  Best regards.
                  • 6. Re: [Tip] How to protect Image file
                    SunghyunWang_(bruce) Level 1
                    If..................... somebody can create an object which containing your decoded script string, and attach it to the Movie clip you created, it's... done. Hmm... interesting.... I will also find.........

                    Thank you for good idea.