Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Compute a checksum on the iPhone from NSData

Tags:

iphone

nsdata

Using the iPhone SDK, I'm having the user select images from the image picker. If the user selects an image they've selected before, I'd like to make the user aware of it.

My initial plan (just to make sure other things work for now) is to save the image to a file (need to do this anyway for other reasons), using a checksum of the NSData as the filename. Then, when they select the same image later on, the checksum will be the same and so I can see that a file with that name already exists - hurrah!

However, I've scoured the internet and the Apple docs for how to compute a checksum from a NSData. I know I could implement my own implementation, but I'd prefer to avoid that, if possible. I'm also happy for other ideas of how to check that two UIImages are the same.

EDIT

Two years ago I promised a code sample, and here it is. Really sorry for the delay! :)

+(NSString*)imageIdForData:(NSData*)data
{
        char* result = (char*) [[data MD5Sum] bytes];

        NSString* hash =  [NSString stringWithFormat: @"%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X",
                                           result[0], result[1],
                                           result[2], result[3],
                                           result[4], result[5],
                                           result[6], result[7],
                                           result[8], result[9],
                                           result[10], result[11],
                                           result[12], result[13],
                                           result[14], result[15]];

        return hash;
}
like image 369
Itay Avatar asked Jun 22 '09 18:06

Itay


2 Answers

Because everything is better with categories...

Header:

@interface NSData (MD5)
- (NSString *)md5String;
@end

Implementation:

#import <CommonCrypto/CommonDigest.h>


- (NSString *)md5String
{
    void *cData = malloc([self length]);
    unsigned char resultCString[16];
    [self getBytes:cData length:[self length]];

    CC_MD5(cData, (unsigned int)[self length], resultCString);
    free(cData);

    NSString *result = [NSString stringWithFormat:
                        @"%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X",
                        resultCString[0], resultCString[1], resultCString[2], resultCString[3],
                        resultCString[4], resultCString[5], resultCString[6], resultCString[7],
                        resultCString[8], resultCString[9], resultCString[10], resultCString[11],
                        resultCString[12], resultCString[13], resultCString[14], resultCString[15]
                        ];
    return result;
}
like image 175
BadPirate Avatar answered Oct 23 '22 17:10

BadPirate


In the <CommonCrypto/CommonDigest.h> header file there should be a CC_MD5 function that will compute an MD5 hash of arbitrary data. It's a C function, so it won't work directly on an NSData, but it should do what you need.

Some more info here (including a wrapper using NSString - should be easy enough to convert to use NSData)

like image 36
Eric Petroelje Avatar answered Oct 23 '22 18:10

Eric Petroelje