Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1419)

Side by Side Diff: chrome/browser/chrome_browser_application_mac.mm

Issue 7038010: [Mac] Allow NSExceptions in certain cases. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Oh, clang, you crazy fox. Created 9 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « base/mac/scoped_nsexception_enabler.mm ('k') | printing/printing_context_mac.mm » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #import "chrome/browser/chrome_browser_application_mac.h" 5 #import "chrome/browser/chrome_browser_application_mac.h"
6 6
7 #import "base/logging.h" 7 #import "base/logging.h"
8 #import "base/mac/scoped_nsexception_enabler.h"
8 #import "base/metrics/histogram.h" 9 #import "base/metrics/histogram.h"
9 #import "base/memory/scoped_nsobject.h" 10 #import "base/memory/scoped_nsobject.h"
10 #import "base/sys_string_conversions.h" 11 #import "base/sys_string_conversions.h"
11 #import "chrome/app/breakpad_mac.h" 12 #import "chrome/app/breakpad_mac.h"
12 #include "chrome/browser/accessibility/browser_accessibility_state.h" 13 #include "chrome/browser/accessibility/browser_accessibility_state.h"
13 #import "chrome/browser/app_controller_mac.h" 14 #import "chrome/browser/app_controller_mac.h"
14 #include "chrome/browser/ui/browser_list.h" 15 #include "chrome/browser/ui/browser_list.h"
15 #import "chrome/browser/ui/cocoa/objc_method_swizzle.h" 16 #import "chrome/browser/ui/cocoa/objc_method_swizzle.h"
16 #import "chrome/browser/ui/cocoa/objc_zombie.h" 17 #import "chrome/browser/ui/cocoa/objc_zombie.h"
17 #include "chrome/browser/ui/tab_contents/tab_contents_wrapper.h" 18 #include "chrome/browser/ui/tab_contents/tab_contents_wrapper.h"
(...skipping 68 matching lines...) Expand 10 before | Expand all | Expand 10 after
86 if (aName == NSInvalidArgumentException) { 87 if (aName == NSInvalidArgumentException) {
87 fatal = YES; 88 fatal = YES;
88 } 89 }
89 90
90 // Dear reader: Something you just did provoked an NSException. 91 // Dear reader: Something you just did provoked an NSException.
91 // NSException is implemented in terms of setjmp()/longjmp(), 92 // NSException is implemented in terms of setjmp()/longjmp(),
92 // which does poor things when combined with C++ scoping 93 // which does poor things when combined with C++ scoping
93 // (destructors are skipped). Chrome should be NSException-free, 94 // (destructors are skipped). Chrome should be NSException-free,
94 // please check your backtrace and see if you can't file a bug 95 // please check your backtrace and see if you can't file a bug
95 // with a repro case. 96 // with a repro case.
96 if (fatal) { 97 const bool allow = base::mac::GetNSExceptionsAllowed();
98 if (fatal && !allow) {
97 LOG(FATAL) << "Someone is trying to raise an exception! " 99 LOG(FATAL) << "Someone is trying to raise an exception! "
98 << base::SysNSStringToUTF8(value); 100 << base::SysNSStringToUTF8(value);
99 } else { 101 } else {
100 // Make sure that developers see when their code throws 102 // Make sure that developers see when their code throws
101 // exceptions. 103 // exceptions.
102 DLOG(ERROR) << "Someone is trying to raise an exception! " 104 DLOG(ERROR) << "Someone is trying to raise an exception! "
103 << base::SysNSStringToUTF8(value); 105 << base::SysNSStringToUTF8(value);
104 NOTREACHED(); 106 DCHECK(allow);
105 } 107 }
106 } 108 }
107 109
108 // Forward to the original version. 110 // Forward to the original version.
109 return gOriginalInitIMP(self, _cmd, aName, aReason, someUserInfo); 111 return gOriginalInitIMP(self, _cmd, aName, aReason, someUserInfo);
110 } 112 }
111 @end 113 @end
112 114
113 namespace chrome_browser_application_mac { 115 namespace chrome_browser_application_mac {
114 116
(...skipping 207 matching lines...) Expand 10 before | Expand all | Expand 10 after
322 } else if ([sender isKindOfClass:[NSMenuItem class]]) { 324 } else if ([sender isKindOfClass:[NSMenuItem class]]) {
323 tag = [sender tag]; 325 tag = [sender tag];
324 } 326 }
325 327
326 NSString* actionString = NSStringFromSelector(anAction); 328 NSString* actionString = NSStringFromSelector(anAction);
327 NSString* value = 329 NSString* value =
328 [NSString stringWithFormat:@"%@ tag %d sending %@ to %p", 330 [NSString stringWithFormat:@"%@ tag %d sending %@ to %p",
329 [sender className], tag, actionString, aTarget]; 331 [sender className], tag, actionString, aTarget];
330 332
331 ScopedCrashKey key(kActionKey, value); 333 ScopedCrashKey key(kActionKey, value);
334
335 // Certain third-party code, such as print drivers, can still throw
336 // exceptions and Chromium cannot fix them. This provides a way to
337 // work around those on a spot basis.
338 bool enableNSExceptions = false;
339
340 // http://crbug.com/80686 , an Epson printer driver.
341 if (anAction == @selector(selectPDE:)) {
342 enableNSExceptions = true;
343 }
344
345 // Minimize the window by keeping this close to the super call.
346 scoped_ptr<base::mac::ScopedNSExceptionEnabler> enabler(NULL);
347 if (enableNSExceptions)
348 enabler.reset(new base::mac::ScopedNSExceptionEnabler());
332 return [super sendAction:anAction to:aTarget from:sender]; 349 return [super sendAction:anAction to:aTarget from:sender];
333 } 350 }
334 351
335 // NSExceptions which are caught by the event loop are logged here. 352 // NSExceptions which are caught by the event loop are logged here.
336 // NSException uses setjmp/longjmp, which can be very bad for C++, so 353 // NSException uses setjmp/longjmp, which can be very bad for C++, so
337 // we attempt to track and report them. 354 // we attempt to track and report them.
338 - (void)reportException:(NSException *)anException { 355 - (void)reportException:(NSException *)anException {
339 // If we throw an exception in this code, we can create an infinite 356 // If we throw an exception in this code, we can create an infinite
340 // loop. If we throw out of the if() without resetting 357 // loop. If we throw out of the if() without resetting
341 // |reportException|, we'll stop reporting exceptions for this run. 358 // |reportException|, we'll stop reporting exceptions for this run.
342 static BOOL reportingException = NO; 359 static BOOL reportingException = NO;
343 DCHECK(!reportingException); 360 DCHECK(!reportingException);
344 if (!reportingException) { 361 if (!reportingException) {
345 reportingException = YES; 362 reportingException = YES;
346 chrome_browser_application_mac::RecordExceptionWithUma(anException); 363 chrome_browser_application_mac::RecordExceptionWithUma(anException);
347 364
348 // http://crbug.com/45928 is a bug about needing to double-close 365 // http://crbug.com/45928 is a bug about needing to double-close
349 // windows sometimes. One theory is that |-isHandlingSendEvent| 366 // windows sometimes. One theory is that |-isHandlingSendEvent|
350 // gets latched to always return |YES|. Since scopers are used to 367 // gets latched to always return |YES|. Since scopers are used to
351 // manipulate that value, that should not be possible. One way to 368 // manipulate that value, that should not be possible. One way to
352 // sidestep scopers is setjmp/longjmp (see above). The following 369 // sidestep scopers is setjmp/longjmp (see above). The following
353 // is to "fix" this while the more fundamental concern is 370 // is to "fix" this while the more fundamental concern is
354 // addressed elsewhere. 371 // addressed elsewhere.
355 [self clearIsHandlingSendEvent]; 372 [self clearIsHandlingSendEvent];
356 373
374 // If |ScopedNSExceptionEnabler| is used to allow exceptions, and an
375 // uncaught exception is thrown, it will throw past all of the scopers.
376 // Reset the flag so that future exceptions are not masked.
377 base::mac::SetNSExceptionsAllowed(false);
378
357 // Store some human-readable information in breakpad keys in case 379 // Store some human-readable information in breakpad keys in case
358 // there is a crash. Since breakpad does not provide infinite 380 // there is a crash. Since breakpad does not provide infinite
359 // storage, we track two exceptions. The first exception thrown 381 // storage, we track two exceptions. The first exception thrown
360 // is tracked because it may be the one which caused the system to 382 // is tracked because it may be the one which caused the system to
361 // go off the rails. The last exception thrown is tracked because 383 // go off the rails. The last exception thrown is tracked because
362 // it may be the one most directly associated with the crash. 384 // it may be the one most directly associated with the crash.
363 static NSString* const kFirstExceptionKey = @"firstexception"; 385 static NSString* const kFirstExceptionKey = @"firstexception";
364 static BOOL trackedFirstException = NO; 386 static BOOL trackedFirstException = NO;
365 static NSString* const kLastExceptionKey = @"lastexception"; 387 static NSString* const kLastExceptionKey = @"lastexception";
366 388
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
399 if (RenderViewHost* rvh = contents->render_view_host()) { 421 if (RenderViewHost* rvh = contents->render_view_host()) {
400 rvh->EnableRendererAccessibility(); 422 rvh->EnableRendererAccessibility();
401 } 423 }
402 } 424 }
403 } 425 }
404 } 426 }
405 return [super accessibilitySetValue:value forAttribute:attribute]; 427 return [super accessibilitySetValue:value forAttribute:attribute];
406 } 428 }
407 429
408 @end 430 @end
OLDNEW
« no previous file with comments | « base/mac/scoped_nsexception_enabler.mm ('k') | printing/printing_context_mac.mm » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698