Ver código fonte

Fix #168 by restructuring try-catch branching

ThePantsThief 9 anos atrás
pai
commit
9e9704580a
1 arquivos alterados com 31 adições e 30 exclusões
  1. 31 30
      Classes/Utility/FLEXRuntimeUtility.m

+ 31 - 30
Classes/Utility/FLEXRuntimeUtility.m

@@ -353,66 +353,67 @@ const unsigned int kFLEXNumberOfImplicitArgs = 2;
                     return nil;
                 }
                 
-                NSUInteger bufferSize = 0;
                 @try {
+                    NSUInteger bufferSize = 0;
+                    
                     // NSGetSizeAndAlignment barfs on type encoding for bitfields.
                     NSGetSizeAndAlignment(typeEncodingCString, &bufferSize, NULL);
+                    
+                    if (bufferSize > 0) {
+                        void *buffer = calloc(bufferSize, 1);
+                        [argumentValue getValue:buffer];
+                        [invocation setArgument:buffer atIndex:argumentIndex];
+                        free(buffer);
+                    }
                 } @catch (NSException *exception) { }
-                
-                if (bufferSize > 0) {
-                    void *buffer = calloc(bufferSize, 1);
-                    [argumentValue getValue:buffer];
-                    [invocation setArgument:buffer atIndex:argumentIndex];
-                    free(buffer);
-                }
             }
         }
     }
     
     // Try to invoke the invocation but guard against an exception being thrown.
-    BOOL successfullyInvoked = NO;
+    id returnObject = nil;
     @try {
         // Some methods are not fit to be called...
         // Looking at you -[UIResponder(UITextInputAdditions) _caretRect]
         [invocation invoke];
-        successfullyInvoked = YES;
+        
+        // Retreive the return value and box if necessary.
+        const char *returnType = [methodSignature methodReturnType];
+        
+        if (returnType[0] == @encode(id)[0] || returnType[0] == @encode(Class)[0]) {
+            // Return value is an object.
+            __unsafe_unretained id objectReturnedFromMethod = nil;
+            [invocation getReturnValue:&objectReturnedFromMethod];
+            returnObject = objectReturnedFromMethod;
+        } else if (returnType[0] != @encode(void)[0]) {
+            // Will use arbitrary buffer for return value and box it.
+            void *returnValue = malloc([methodSignature methodReturnLength]);
+            
+            if (returnValue) {
+                [invocation getReturnValue:returnValue];
+                returnObject = [self valueForPrimitivePointer:returnValue objCType:returnType];
+                free(returnValue);
+            }
+        }
     } @catch (NSException *exception) {
         // Bummer...
         if (error) {
             // "… on <class>" / "… on instance of <class>"
             NSString *class = NSStringFromClass([object class]);
             NSString *calledOn = object == [object class] ? class : [@"an instance of " stringByAppendingString:class];
-
+            
             NSString *message = [NSString stringWithFormat:@"Exception '%@' thrown while performing selector '%@' on %@.\nReason:\n\n%@",
                                  exception.name,
                                  NSStringFromSelector(selector),
                                  calledOn,
                                  exception.reason];
-
+            
             *error = [NSError errorWithDomain:FLEXRuntimeUtilityErrorDomain
                                          code:FLEXRuntimeUtilityErrorCodeInvocationFailed
                                      userInfo:@{ NSLocalizedDescriptionKey : message }];
         }
     }
     
-    // Retreive the return value and box if necessary.
-    id returnObject = nil;
-    if (successfullyInvoked) {
-        const char *returnType = [methodSignature methodReturnType];
-        if (returnType[0] == @encode(id)[0] || returnType[0] == @encode(Class)[0]) {
-            __unsafe_unretained id objectReturnedFromMethod = nil;
-            [invocation getReturnValue:&objectReturnedFromMethod];
-            returnObject = objectReturnedFromMethod;
-        } else if (returnType[0] != @encode(void)[0]) {
-            void *returnValue = malloc([methodSignature methodReturnLength]);
-            if (returnValue) {
-                [invocation getReturnValue:returnValue];
-                returnObject = [self valueForPrimitivePointer:returnValue objCType:returnType];
-                free(returnValue);
-            }
-        }
-    }
-    
     return returnObject;
 }