Jamoma API  0.6.0.a19
CAXException.h
1 /* Copyright © 2007 Apple Inc. All Rights Reserved.
2 
3  Disclaimer: IMPORTANT: This Apple software is supplied to you by
4  Apple Inc. ("Apple") in consideration of your agreement to the
5  following terms, and your use, installation, modification or
6  redistribution of this Apple software constitutes acceptance of these
7  terms. If you do not agree with these terms, please do not use,
8  install, modify or redistribute this Apple software.
9 
10  In consideration of your agreement to abide by the following terms, and
11  subject to these terms, Apple grants you a personal, non-exclusive
12  license, under Apple's copyrights in this original Apple software (the
13  "Apple Software"), to use, reproduce, modify and redistribute the Apple
14  Software, with or without modifications, in source and/or binary forms;
15  provided that if you redistribute the Apple Software in its entirety and
16  without modifications, you must retain this notice and the following
17  text and disclaimers in all such redistributions of the Apple Software.
18  Neither the name, trademarks, service marks or logos of Apple Inc.
19  may be used to endorse or promote products derived from the Apple
20  Software without specific prior written permission from Apple. Except
21  as expressly stated in this notice, no other rights or licenses, express
22  or implied, are granted by Apple herein, including but not limited to
23  any patent rights that may be infringed by your derivative works or by
24  other works in which the Apple Software may be incorporated.
25 
26  The Apple Software is provided by Apple on an "AS IS" basis. APPLE
27  MAKES NO WARRANTIES, EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION
28  THE IMPLIED WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY AND FITNESS
29  FOR A PARTICULAR PURPOSE, REGARDING THE APPLE SOFTWARE OR ITS USE AND
30  OPERATION ALONE OR IN COMBINATION WITH YOUR PRODUCTS.
31 
32  IN NO EVENT SHALL APPLE BE LIABLE FOR ANY SPECIAL, INDIRECT, INCIDENTAL
33  OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
34  SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
35  INTERRUPTION) ARISING IN ANY WAY OUT OF THE USE, REPRODUCTION,
36  MODIFICATION AND/OR DISTRIBUTION OF THE APPLE SOFTWARE, HOWEVER CAUSED
37  AND WHETHER UNDER THEORY OF CONTRACT, TORT (INCLUDING NEGLIGENCE),
38  STRICT LIABILITY OR OTHERWISE, EVEN IF APPLE HAS BEEN ADVISED OF THE
39  POSSIBILITY OF SUCH DAMAGE.
40 */
41 #ifndef __CAXException_h__
42 #define __CAXException_h__
43 
44 #if !defined(__COREAUDIO_USE_FLAT_INCLUDES__)
45  #include <CoreFoundation/CoreFoundation.h>
46 #else
47  #include <ConditionalMacros.h>
48  #include <CoreFoundation.h>
49 #endif
50 #include "CADebugMacros.h"
51 #include <ctype.h>
52 //#include <stdio.h>
53 #include <string.h>
54 
55 
56 class CAX4CCString {
57 public:
58  CAX4CCString(OSStatus error) {
59  // see if it appears to be a 4-char-code
60  char *str = mStr;
61  *(UInt32 *)(str + 1) = CFSwapInt32HostToBig(error);
62  if (isprint(str[1]) && isprint(str[2]) && isprint(str[3]) && isprint(str[4])) {
63  str[0] = str[5] = '\'';
64  str[6] = '\0';
65  } else if (error > -200000 && error < 200000)
66  // no, format it as an integer
67  sprintf(str, "%d", (int)error);
68  else
69  sprintf(str, "0x%x", (int)error);
70  }
71  const char *get() const { return mStr; }
72  operator const char *() const { return mStr; }
73 private:
74  char mStr[16];
75 };
76 
77 // An extended exception class that includes the name of the failed operation
78 class CAXException {
79 public:
80  CAXException(const char *operation, OSStatus err) :
81  mError(err)
82  {
83  if (operation == NULL)
84  mOperation[0] = '\0';
85  else if (strlen(operation) >= sizeof(mOperation)) {
86  memcpy(mOperation, operation, sizeof(mOperation) - 1);
87  mOperation[sizeof(mOperation) - 1] = '\0';
88  } else
89 
90  strlcpy(mOperation, operation, sizeof(mOperation));
91  }
92 
93  char *FormatError(char *str) const
94  {
95  return FormatError(str, mError);
96  }
97 
98  char mOperation[256];
99  const OSStatus mError;
100 
101  // -------------------------------------------------
102 
103  typedef void (*WarningHandler)(const char *msg, OSStatus err);
104 
105  static char *FormatError(char *str, OSStatus error)
106  {
107  strcpy(str, CAX4CCString(error));
108  return str;
109  }
110 
111  static void Warning(const char *s, OSStatus error)
112  {
113  if (sWarningHandler)
114  (*sWarningHandler)(s, error);
115  }
116 
117  static void SetWarningHandler(WarningHandler f) { sWarningHandler = f; }
118 private:
119  static WarningHandler sWarningHandler;
120 };
121 
122 #if DEBUG || CoreAudio_Debug
123  #define XThrowIfError(error, operation) \
124  do { \
125  OSStatus __err = error; \
126  if (__err) { \
127  DebugMessageN2("about to throw %s: %s", CAX4CCString(__err).get(), operation);\
128  STOP; \
129  throw CAXException(operation, __err); \
130  } \
131  } while (0)
132 
133  #define XThrowIf(condition, error, operation) \
134  do { \
135  if (condition) { \
136  OSStatus __err = error; \
137  DebugMessageN2("about to throw %s: %s", CAX4CCString(__err).get(), operation);\
138  STOP; \
139  throw CAXException(operation, __err); \
140  } \
141  } while (0)
142 
143  #define XRequireNoError(error, label) \
144  do { \
145  OSStatus __err = error; \
146  if (__err) { \
147  DebugMessageN2("about to throw %s: %s", CAX4CCString(__err).get(), #error);\
148  STOP; \
149  goto label; \
150  } \
151  } while (0)
152 
153  #define XAssert(assertion) \
154  do { \
155  if (!(assertion)) { \
156  DebugMessageN1("error: failed assertion: %s", #assertion); \
157  STOP; \
158  } \
159  } while (0)
160 
161  #define XAssertNoError(error) \
162  do { \
163  OSStatus __err = error; \
164  if (__err) { \
165  DebugMessageN2("error %s: %s", CAX4CCString(__err).get(), #error);\
166  STOP; \
167  } \
168  } while (0)
169 
170  #define ca_require_noerr(errorCode, exceptionLabel) \
171  do \
172  { \
173  int evalOnceErrorCode = (errorCode); \
174  if ( __builtin_expect(0 != evalOnceErrorCode, 0) ) \
175  { \
176  DebugMessageN5("ca_require_noerr: [%s, %d] (goto %s;) %s:%d", \
177  #errorCode, evalOnceErrorCode, \
178  #exceptionLabel, \
179  __FILE__, \
180  __LINE__); \
181  goto exceptionLabel; \
182  } \
183  } while ( 0 )
184 
185  #define ca_verify_noerr(errorCode) \
186  do \
187  { \
188  int evalOnceErrorCode = (errorCode); \
189  if ( __builtin_expect(0 != evalOnceErrorCode, 0) ) \
190  { \
191  DebugMessageN4("ca_verify_noerr: [%s, %d] %s:%d", \
192  #errorCode, evalOnceErrorCode, \
193  __FILE__, \
194  __LINE__); \
195  } \
196  } while ( 0 )
197 
198  #define ca_debug_string(message) \
199  do \
200  { \
201  DebugMessageN3("ca_debug_string: %s %s:%d", \
202  message, \
203  __FILE__, \
204  __LINE__); \
205  } while ( 0 )
206 
207 
208  #define ca_verify(assertion) \
209  do \
210  { \
211  if ( __builtin_expect(!(assertion), 0) ) \
212  { \
213  DebugMessageN3("ca_verify: %s %s:%d", \
214  #assertion, \
215  __FILE__, \
216  __LINE__); \
217  } \
218  } while ( 0 )
219 
220  #define ca_require(assertion, exceptionLabel) \
221  do \
222  { \
223  if ( __builtin_expect(!(assertion), 0) ) \
224  { \
225  DebugMessageN4("ca_require: %s %s %s:%d", \
226  #assertion, \
227  #exceptionLabel, \
228  __FILE__, \
229  __LINE__); \
230  goto exceptionLabel; \
231  } \
232  } while ( 0 )
233 
234  #define ca_check(assertion) \
235  do \
236  { \
237  if ( __builtin_expect(!(assertion), 0) ) \
238  { \
239  DebugMessageN3("ca_check: %s %s:%d", \
240  #assertion, \
241  __FILE__, \
242  __LINE__); \
243  } \
244  } while ( 0 )
245 
246 #else
247  #define XThrowIfError(error, operation) \
248  do { \
249  OSStatus __err = error; \
250  if (__err) { \
251  throw CAXException(operation, __err); \
252  } \
253  } while (0)
254 
255  #define XThrowIf(condition, error, operation) \
256  do { \
257  if (condition) { \
258  OSStatus __err = error; \
259  throw CAXException(operation, __err); \
260  } \
261  } while (0)
262 
263  #define XRequireNoError(error, label) \
264  do { \
265  OSStatus __err = error; \
266  if (__err) { \
267  goto label; \
268  } \
269  } while (0)
270 
271  #define XAssert(assertion) \
272  do { \
273  } while (0)
274 
275  #define XAssertNoError(error) \
276  do { \
277  /*OSStatus __err =*/ error; \
278  } while (0)
279 
280  #define ca_require_noerr(errorCode, exceptionLabel) \
281  do \
282  { \
283  if ( __builtin_expect(0 != (errorCode), 0) ) \
284  { \
285  goto exceptionLabel; \
286  } \
287  } while ( 0 )
288 
289  #define ca_verify_noerr(errorCode) \
290  do \
291  { \
292  if ( 0 != (errorCode) ) \
293  { \
294  } \
295  } while ( 0 )
296 
297  #define ca_debug_string(message)
298 
299  #define ca_verify(assertion) \
300  do \
301  { \
302  if ( !(assertion) ) \
303  { \
304  } \
305  } while ( 0 )
306 
307  #define ca_require(assertion, exceptionLabel) \
308  do \
309  { \
310  if ( __builtin_expect(!(assertion), 0) ) \
311  { \
312  goto exceptionLabel; \
313  } \
314  } while ( 0 )
315 
316  #define ca_check(assertion) \
317  do \
318  { \
319  if ( !(assertion) ) \
320  { \
321  } \
322  } while ( 0 )
323 
324 
325 #endif
326 
327 #define XThrow(error, operation) XThrowIf(true, error, operation)
328 #define XThrowIfErr(error) XThrowIfError(error, #error)
329 
330 #endif // __CAXException_h__