ColdFusion 10 - Hashing Binary Data And Byte Arrays

Posted March 30, 2012 at 9:53 AM by Ben Nadel

Tags: ColdFusion

For years, ColdFusion has had the hash() function for taking variable-length string data and creating one-way "fingerprints" of the original value. This function has changed over time to include algorithm and encoding options; but, it has always worked with string data. Now, with ColdFusion 10, the hash() function has been enhanced to accept binary data (aka. byte arrays). This means that we can now create one-way "fingerprints" of binary values.

NOTE: At the time of this writing, ColdFusion 10 was in public beta.

To demonstrate, let's read in an image file in binary format and output the hash of the image's binary data:

  • <cfscript>
  •  
  • // Read in the raw Binary data of the image.
  • imageBinary = fileReadBinary( expandPath( "./gina_carano.jpg" ) );
  •  
  • // Get the hash of the byte array (that IS the image).
  • imageHash = hash( imageBinary );
  •  
  • // Output the image "fingerprint".
  • writeOutput( "Fingerprint: " & hash( imageBinary ) );
  •  
  • </cfscript>

As you can see, the first argument of the hash() function can now accept a byte array. When we run the above code, we get the following output:

Fingerprint: AF56CD049055F6D00C6DCFFD62C29427

As you can see, the default MD5 algorithm has taken our byte array (binary data) and returned our standard 32-character Hexadecimal string.

Out of curiosity, I wanted to see how the hashing of a Binary value would relate to the hashing of its String representation. As such, I tried using the hash() function to hash both a TXT file and the string content contained within that TXT file:

  • <cfscript>
  •  
  • // Create our string message.
  • message = "It's Friday, Friday - you gotta get down on Friday!";
  •  
  • // Write message to file.
  • fileWrite( expandPath( "./message.txt" ), message );
  •  
  • // Read the message in as binary.
  • messageBinary = fileReadBinary( expandPath( "./message.txt" ) );
  •  
  •  
  • // Output the string "fingerprint".
  • writeOutput( "STR Fingerprint: " & hash( message ) & "<br />" );
  •  
  • // Output the binary "fingerprint".
  • writeOutput( "BIN Fingerprint: " & hash( messageBinary ) );
  •  
  • </cfscript>

This time, when we run the above code, we get the following output:

STR Fingerprint: 60408C08C4AB05073FCEC10FAAE3915E
BIN Fingerprint: 60408C08C4AB05073FCEC10FAAE3915E

Here, you can see that the hash() of the string content was the same as the hash of the file itself. I don't really have any conclusions to draw from this last experiment - it was just an interesting thing to see. And, since each string character is defined by a single byte, this equivalence relationship probably makes sense.

As a final note, I should also point out that the hash() function now takes an argument that defines the number of hashing iterations to apply to the target value. The number-of-iterations enhancement is a security feature and is beyond what I would be able to explain in a meaningful way. I'll defer to the security experts to elucidate that one.


You Might Also Be Interested In:



Reader Comments

Mar 30, 2012 at 4:20 PM // reply »
13 Comments

Nice! You could check if a image has been modified by comparing the fingerprint of two identical images. In some scenarios it can be useful, like document storage and cms systems and like.


Mar 31, 2012 at 9:24 AM // reply »
11,238 Comments

@Marko,

I believe you could do that. Though, in my testing, I did find out that the binary data was different from the value returned from imageGetBlob() on a ColdFusion image of the same data. So, you just have to be careful that you're always accessing the raw binary data when doing the comparison.


Apr 2, 2012 at 10:02 AM // reply »
11,238 Comments

@All,

After this post, I got to thinking about fun ways that we could use images. As such, I wanted to do a quick exploration of hashing byte arrays before ColdFusion 10:

http://www.bennadel.com/blog/2357-Hashing-Byte-Arrays-Binary-Data-With-ColdFusion-Before-ColdFusion-10.htm

Here, I'm using the underlying Java layer to dip down into the some more manual hashing approaches.


Apr 2, 2012 at 10:43 AM // reply »
170 Comments

Ben:

I think all CF10 is doing is running the equivalent of toString() on binary data. If I change:

writeOutput( "BIN Fingerprint: " & hash( messageBinary ) );

to:

writeOutput( "BIN Fingerprint: " & hash( toString(messageBinary) ) );

It works fine in pre-CF10 (I get the same md5 sig as you show.)

So it's certainly convenient that it auto converts the values for you, but it should be easily enough to recreate in pre-CF10.


Apr 2, 2012 at 10:46 AM // reply »
11,238 Comments

@Dan,

When the underlying data is "String" data, I think you are exactly right. But this morning, I was playing around with hashing image data and the toString() method was not working - at least, I don't think it was working. For image data, I had to resort to dipping down into Java.


Apr 2, 2012 at 10:52 AM // reply »
170 Comments

I was able to get it working fine w/an image using fileReadBinary(). I tested it before posting my comment.


Apr 2, 2012 at 10:57 AM // reply »
11,238 Comments

@Dan,

Hmmm, very strange! I am not sure why I am getting a different value (than CF10 hash). I wonder if it has to do with the type of image I am loading.


Post A Comment

Comment Etiquette: Please do not post spam. Please keep the comments on-topic. Please do not post unrelated questions or large chunks of code. And, above all, please be nice to each other - we're trying to have a good conversation here.

Please review the following issues:

Author Name:


Author Email:

Author Website:

Comment:

Supported HTML tags for formatting: <strong>bold</strong>   <em>italic</em>   <code>code</code>







  • Help Wanted - Find Your Next ColdFusion Job
Ben Nadel's Company - Epicenter Consulting Recent Blog Comments
May 17, 2013 at 7:42 PM
HashKeyCopier - An AngularJS Utility Class For Merging Cached And Live Data
Ben - thanks so much for posting these Angular articles and findings, they've been a huge help towards learning one of the more 'complex' JavaScript frameworks out there (IMO). I have been using Angu ... read »
May 16, 2013 at 5:01 PM
UPDATE: Parsing CSV Data Files In ColdFusion With csvToArray()
Your code was the closest thing I've found to obtaining some direction for converting ISO fields to values that CF can translate properly. Thank you for posting! ... read »
May 15, 2013 at 10:37 PM
Very Simple Pusher And ColdFusion Powered Chat
hi id making plz easy ... read »
May 15, 2013 at 6:07 PM
Making SOAP Web Service Requests With ColdFusion And CFHTTP
Ben, you once again saved my bacon at work. Thank you, thank you, thank you! ... read »
May 15, 2013 at 4:15 PM
What If All User Interface (UI) Data Came In Reports?
@Josh, Thanks! @Ben, I definitely recommend the David West book "Object Thinking" I've been quoting from. It goes deeply into the philosophy and history of OO programming. His breadth ... read »
May 15, 2013 at 11:36 AM
Ask Ben: Print Part Of A Web Page With jQuery
I found this helpfull when you need to keep (refresh) the original parent page after closing the iframe child print dialog (Hoping you're not using a form at this time so it won't submit again): On ... read »
May 14, 2013 at 7:13 PM
What If All User Interface (UI) Data Came In Reports?
@Jonah, If there's any books you'd recommend on the subject of domain modelling, I'd love to hear it. I just downloaded the free PDF of "Domain Driven Design Quickly". Figured I'd give it ... read »
May 14, 2013 at 6:57 PM
The UX Of Prototyping: Low-Fidelity Is The New High-Fidelity
@Phillip, I'm not sure I follow what you mean? Are you saying that you looked at the list of widgets provided by the jQuery UI and let that be your style guide? ... read »
InVision App - Prototyping Made Beautiful With Prototyping Tools