Showing posts with label security. Show all posts
Showing posts with label security. Show all posts

Tuesday, August 16, 2016

iOS Format String Attacks

Validating and sanitizing user input is very important and mandatory in any application which takes user input. As user who is using our application is the most untrusted source in case of user input.

All the text input fields entires should be validated or sanity checked. Some examples are,

  • Empty text entry
  • Spaces at the beginning and ending (Trimming)
  • Restricted characters (phone number shouldn't contain alphabets)
  • Special characters
  • Email validation
  • Proper length checking

If we don't validate and use these text entries inside our app or sending them to server as parameters, the application will definitely goes out of your control.

Specially incase of strings we should clearly mention the format. Otherwise it's a chance to attackers to format a string of their own.

Let's see some examples of string attacks.

I have a search textfield and I need to store the search strings of user for auto fill.


      
    NSString *searchStr = self.searchTF.text;
    NSLog(searchStr);


I haven't validated the search string and just logging in this case for demo though we need to send it to server for logs. Let's see the NSLog output If user enters 'iPhone \n  iPad \n iPod' and obviously there will be no search results.

 iPhone 
 iPad 
 iPod

This is the output because of malfunctioned search string input by an attacker. Let's say these are stored in the server logs. When you take the report, It will show obviously wrong statistics.

App user searched for iPhone
App user searched for iPad
App user searched for iPod

If you observe, As we have not validated the user input, Our server logs are going wrong when we take reports.

In the same way, What If user enters '%x%x%x' as search string and we use it without validating and formatting it.


      
    NSString *searchStr = @"%x%x%x";
    NSLog(searchStr);      // 4f06800


It is printing the application memory addresses which is a security breach. Using this memory addresses, attackers can read/write/delete data from application memory.

To avoid all these, It is a good practice to validate or sanitize the input data always and use the format specifier %@ while displaying or using strings.

In the above case, If we use format specifier (%@),


      
    NSString *searchStr = @"%x%x%x";
    NSLog(@"%@",searchStr);    // %x%x%x


It is exactly what user has entered in the search field. 

Not only in the Log statements, Whenever there is a string format we are using,

  • stringWithFormat
  • initWithFormat
  • appendWithFormat

It is a good practice to format the string.


Hope this post is useful. Feel free to comment incase of any queries.


Monday, August 15, 2016

iOS Jailbreak Unchecked File Operation Result Code

In general, We use temporary files to save data for temporary purpose in our application. 
We save in plists, txt files etc..

But we developers least bother about the error codes of these file operations. We simply write,


      
      NSError *error = nil;
      [data writeToFile:pathToFile options:NSDataWritingAtomic error:&error];


and not even check the result code whether the write operation is successful or not. This may cause a security breach.

These insecure file operations are a major source of security vulnerabilities. They could be any of below.

Insecure file operations give an attacker the ability to read confidential information.

Attackers can take control of an application or even control of entire system.

Data written  to temporary file may become corrupted. A buffer overflow or or other unintended behaviour may happen when the corrupted file is read back by the application. The application writes data to a temporary file. The write operation fails in the middle. Part of the data is written to the file, and another part is lost. The application does not check the result code of the file operation, and takes no corrective actions. The application reads back the corrupted file, and a buffer overflow or other unintended behavior happens. An attacker exploits the buffer overflow to gain control of the application. 

So it's developer's responsibility to check the result codes of these file operations and take the necessary actions if they fail in the middle.

Fortunately, All the file operations in cocoa gives us the result code whether the operation is successful or not.


      
- (BOOL)writeToFile:(NSString *)path options:(NSDataWritingOptions)writeOptionsMask error:(NSError **)errorPtr;
- (BOOL)writeToURL:(NSURL *)url options:(NSDataWritingOptions)writeOptionsMask error:(NSError **)errorPtr;

- (BOOL)fileExistsAtPath:(NSString *)path;
- (BOOL)fileExistsAtPath:(NSString *)path isDirectory:(nullable BOOL *)isDirectory;
- (BOOL)isReadableFileAtPath:(NSString *)path;
- (BOOL)isWritableFileAtPath:(NSString *)path;
- (BOOL)isExecutableFileAtPath:(NSString *)path;
- (BOOL)isDeletableFileAtPath:(NSString *)path;

- (BOOL)copyItemAtPath:(NSString *)srcPath toPath:(NSString *)dstPath error:(NSError **)error NS_AVAILABLE(10_5, 2_0);
- (BOOL)moveItemAtPath:(NSString *)srcPath toPath:(NSString *)dstPath error:(NSError **)error NS_AVAILABLE(10_5, 2_0);
- (BOOL)linkItemAtPath:(NSString *)srcPath toPath:(NSString *)dstPath error:(NSError **)error NS_AVAILABLE(10_5, 2_0);
- (BOOL)removeItemAtPath:(NSString *)path error:(NSError **)error NS_AVAILABLE(10_5, 2_0);


- (BOOL)copyItemAtURL:(NSURL *)srcURL toURL:(NSURL *)dstURL error:(NSError **)error NS_AVAILABLE(10_6, 4_0);
- (BOOL)moveItemAtURL:(NSURL *)srcURL toURL:(NSURL *)dstURL error:(NSError **)error NS_AVAILABLE(10_6, 4_0);
- (BOOL)linkItemAtURL:(NSURL *)srcURL toURL:(NSURL *)dstURL error:(NSError **)error NS_AVAILABLE(10_6, 4_0);
- (BOOL)removeItemAtURL:(NSURL *)URL error:(NSError **)error NS_AVAILABLE(10_6, 4_0);


As they are returning a BOOL value, We can simple check it and raise exceptions as shown below to avoid these security vulnerabilities.


      
    NSError *writeError;

    if (![encryptedData writeToURL:[NSURL fileURLWithPath:
           [NSString stringWithFormat:@"%@",myPath]] options:
                    NSDataWritingAtomic error:&writeError])
                 
    {
        [[NSException exceptionWithName:@"FileWriteError" reason:
                              [error localizedFailureReason] userInfo:nil] raise];
                               
    }


Always check the results codes as they are free of cost :)


Hope this post is useful. Feel free to comment in case of any queries.


Thursday, August 11, 2016

iOS Screen Caching Security Vulnerability

iOS takes screenshot of current screen opened when app is going background and uses that screenshot for animation while the app is coming to foreground.  So that user will have a nice experience whenever app goes to background and comes to foreground. This may be a security issue if the screen opened is displaying any sensitive data. It is application developer's responsibility to prevent the background screen caching of this sensitive information.

If it's a web application, you might have observed in some websites where they display any sensitive information by masking it as shown below.




      Credit card number    XXXX XXXX XXXX 1234

      Mobile number           XXXXXXX812


In the same way we need to prevent the background screen caching in our application. We an also mask the sensitive data while displaying in UILabels. This masking has to done for each and every label in all the views which displays sensitive data. As this is bit tedious to take care of all the labels in the application, We can mask the entire app window while it is going to background and remove that mask when the app is coming to foreground.

Let me show you how I prevented this screen caching in one of my iOS applications. 

I am taking an UIImageView with a black background color and added it to the application window in AppDelegate's applicationWillResignActive method.



        screenCacheImageView = [[UIImageView alloc]initWithFrame:
                                                                                    [self.window frame]];

        [screenCacheImageView setTintColor:[UIColor blackColor]];

        [screenCacheImageView setBackgroundColor:[UIColor blackColor]];

        [self.window addSubview:screenCacheImageView];



And in the applicationDidBecomeActive method, remove the added black image view mask to prevent background screen caching for the whole application.

      
        if(screenCacheImageView != nil) {

              [screenCacheImageView removeFromSuperview];
              screenCacheImageView = nil;

        }



Hope this post is useful. Feel free to comment incase of any queries.