145

With all the SDKs floating around, it's handy to be able to build for multiple SDKs and platforms. However, bouncing from 3.2 to 3.0 and even occasionally 2.x, I frequently get deprecated warnings involving methods that have changed or been superseded:

warning: 'UIKeyboardBoundsUserInfoKey' is deprecated.

Since I still want to maintain compatibility with older OSes, and I'm also striving to remove 'noise' when building, is there a way to turn off or disable these warnings?

Cœur
  • 37,241
  • 25
  • 195
  • 267
Ben Gottlieb
  • 85,404
  • 22
  • 176
  • 172
  • 4
    While Paul R's answer works, consider that manicaesar is a bit more surgical, in that it allows you to suppress exactly the warning you want, without losing other additional warnings which might be important. It seems to me that, in terms of best-practices, manicaesar has The Correct Answer™ – Olie Jan 18 '13 at 04:23
  • For the **Swift** equivalent of this question, it's: [How to silence a warning in Swift?](https://stackoverflow.com/questions/31540446/how-to-silence-a-warning-in-swift) – Cœur Mar 13 '23 at 09:48

10 Answers10

346

Since I yet can not add a comment to the @samiq post, I think I will expand it. Input mentioned directive before a function / method in which you use deprecated stuff. Then you can restore the previous setting after the definition of the function end:

#pragma GCC diagnostic push 
#pragma GCC diagnostic ignored "-Wdeprecated-declarations"
- (void) methodUsingDeprecatedStuff {
    //use deprecated stuff
}
#pragma GCC diagnostic pop
manicaesar
  • 5,024
  • 3
  • 26
  • 29
  • 1
    Awesome tip! Too bad it can't be declared inside a method. – Dustin May 24 '11 at 16:16
  • 13
    Actually it can be declared inside a method. I just had to do it today due a bug in the docs/sdk – jer Jul 22 '12 at 20:49
  • 7
    +1 A slightly better way is to use the syntax with `#pragma GCC diagnostics push #pragma GCC diagnostics ignored "-Wdeprecated-declarations" .. .. Code here .. .. #pragma GCC diagnostic pop` as this method takes you back to whatever setting was set before.. [http://gcc.gnu.org/onlinedocs/gcc/Diagnostic-Pragmas.html] – Niclas Jan 27 '14 at 14:10
  • 4
    Changed acording to suggestions :) – manicaesar Jan 27 '14 at 14:16
  • what is the equivalent for this in swift? – Hogdotmac Jul 03 '19 at 11:33
  • @Hogdotmac last time I checked (Swift 4.1 :P) there was not anything like that in Swift. – manicaesar Nov 04 '19 at 12:49
152

Clang provides a nice feature that makes the "restore" step in the @manicaesar post independent of the initial warning state:

#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wdeprecated-declarations"
- (void) methodUsingDeprecatedStuff {
    //use deprecated stuff
}
#pragma clang diagnostic pop

To quote the Clang manual:

In addition to all of the functionality provided by GCC's pragma, Clang also allows you to push and pop the current warning state. This is particularly useful when writing a header file that will be compiled by other people, because you don't know what warning flags they build with.

Andrew Hershberger
  • 4,152
  • 1
  • 25
  • 35
  • 1
    More recent versions of GCC use the same syntax (substitute clang for GCC). – Niclas Jan 27 '14 at 14:04
  • 3
    I always get confused about what is LLVM, GCC and Clang. So, I wanted to drop a note to save time. GNU Complier Collection (GCC) was used with Xcode 3, then Apple released Xcode 4 with a hybrid LLVM-GCC. Then Low Level Virtual Machine (LLVM) compiler took over, see more info at http://llvm.org. As of Xcode 7.2.1 the default compiler is Apple LLVM 7.0. LLVM compiler is a library of other "projects", debuggers, and other tools, which include the Clang native compiler. Clang is an "LLVM native" C/C++/Objective-C compiler. – serge-k Feb 15 '16 at 17:31
86

Try -Wno-deprecated-declarations, or its corresponding setting in Xcode, GCC_WARN_ABOUT_DEPRECATED_FUNCTIONS (pro tip: just type in "deprecated" in the build settings to find the specific setting for this warning).

Current versions of Xcode (e.g. Xcode 9.2):

enter image description here


Ancient versions of Xcode (e.g. Xcode 2.x, 3.x):

enter image description here

Paul R
  • 208,748
  • 37
  • 389
  • 560
  • 17
    Turns out it's even easier than that; there's a checkbox in the Xcode target settings; your answer prompted me to search there. Thanks! – Ben Gottlieb Apr 12 '10 at 14:20
  • 4
    You can also do this on a per-file basis. See this answer for adding per-file flags: http://stackoverflow.com/a/6658549/272473 – mrwalker Sep 07 '12 at 20:08
  • 5
    answers like this are frustrating for newbs. Try it where? How do I find target settings? A little more explanation would increase the value of this answer. – noogrub Oct 14 '12 at 11:36
  • 1
    @noogrub: this is an old answer from 2010 and relates to Xcode 2.x and 3.x. Xcode 4.x is a very different beast, and uses different compilers, so the answer is probably obsolete by now. – Paul R Oct 14 '12 at 15:12
  • 1
    Thanks, Paul. I was using an older iMac that won't upgrade past 10.5.8, so the older details still apply. I found some more detail elsewhere, appreciate your reply. – noogrub Oct 15 '12 at 14:12
  • 10
    An answer this poorly explained shouldn't be marked as correct. – Chris Hatton Mar 29 '13 at 19:47
  • 6
    Search for "Deprecated" in build settings and you'll see it. – quantumpotato Apr 13 '14 at 14:55
49

Since we tend to need to support older OSes, but pay attention to our warnings, I wanted a tidier way to do this. I put this together, inspired by some Mozilla code:

#define SILENCE_DEPRECATION(expr)                                   \
do {                                                                \
_Pragma("clang diagnostic push")                                    \
_Pragma("clang diagnostic ignored \"-Wdeprecated-declarations\"")   \
expr;                                                               \
_Pragma("clang diagnostic pop")                                     \
} while(0)

#define SILENCE_IOS7_DEPRECATION(expr) SILENCE_DEPRECATION(expr)
#define SILENCE_IOS8_DEPRECATION(expr) SILENCE_DEPRECATION(expr)

This allows you to do the following:

SILENCE_IOS7_DEPRECATION(return [self sizeWithFont:font constrainedToSize:size]);

It also works with blocks of code:

SILENCE_IOS7_DEPRECATION(
    view = [[MKPolylineView alloc] initWithPolyline:self];
    view.lineWidth = self.lineWidth;
    view.strokeColor = self.color;
);

Also, when you do drop support for pre-iOS 7 devices, you can easily search through the code to find the deprecated usages to fix.

Joe Trellick
  • 1,125
  • 7
  • 12
  • this is a the much better long-term solution for most code than clamping down on deprecation (or any other) warnings at a global/project level. terrific answer. – natbro Oct 25 '14 at 20:38
  • That's a very sexy way to solve this common problem. I appreciate your efforts. – Scott D May 13 '15 at 02:47
  • Just as a reference, this can be used for any clang option... I personally use it for this (`-Wdeprecated-declarations`) and for disabling performSelector leaks warning (`-WperformSelector-leaks`). You just need to change the option in the second `_Pragma` call accordingly. – Alejandro Iván Jul 14 '15 at 14:27
  • 1
    Why is the `do { ... } while(0);` required? – Ky - Mar 15 '16 at 19:46
  • 1
    @BenC.R.Leggiero because you're not passing a block but several statements between those parenthesis. You're basically suppressing warnings for every line. – Alejandro Iván Apr 12 '16 at 15:20
  • 1
    @AlejandroIván I know your explanation makes sense to you... but to me, it just looks like you're re-wording the question. Can you explain why `do{...}while(0);` is required here in particular? Why not just `{...}`? Why not `if(true){...}`? etc. – Ky - Apr 12 '16 at 18:45
  • 2
    @BenC.R.Leggiero you're right. For some reason I misread your question. Check the accepted answer here: http://stackoverflow.com/questions/154136/why-use-apparently-meaningless-do-while-and-if-else-statements-in-c-c-macros/154138#154138 – Alejandro Iván Apr 12 '16 at 18:48
  • this is just so beautiful – jere Aug 30 '16 at 21:23
  • I like this a lot in terms of its ramifications for code maintenance. Noob question: does the compiler optimise away the do/while loop? Put another way, does this have any performance impact at run-time? Five years later, is this still the smartest way to go about it? – Alexander Gingell Mar 05 '19 at 19:57
29

You can also suppress warnings per file by using

#pragma GCC diagnostic ignored "-Wdeprecated-declarations"

which in turn makes it a little bit better practice than just suppressing all warning once and together... after all you got to know what you are doing it for.

samiq
  • 2,954
  • 1
  • 29
  • 29
27

If you want to silence warning Implementing deprecated method or Implementing deprecated class, use:


    #pragma clang diagnostic push
    #pragma clang diagnostic ignored "-Wdeprecated-implementations"
    // code
    #pragma clang diagnostic pop

krzysztof
  • 411
  • 4
  • 3
  • 1
    When I saw "-Wdeprecated-declarations", I guess there must be "-Wdeprecated-implementations". And it really works. Thank you. – DawnSong Nov 22 '18 at 02:49
  • "-Wdeprecated-declarations" didn't work for me. "-Wdeprecated-implementations" does work. Thanks. – m8labs Jan 26 '23 at 15:41
9

In your build settings, find Deprecated Functions.

enter image description here

ABCD
  • 7,914
  • 9
  • 54
  • 90
7

If you would like a blanket check for all kinds of deprecations in a piece of code. Please use the -Wdeprecated flag like below:

#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wdeprecated"
- (void) methodUsingDeprecatedStuff {
    //use deprecated stuff
}
#pragma clang diagnostic pop
jarora
  • 5,384
  • 2
  • 34
  • 46
0

Add Filter In issue navigator.

enter image description here

hstdt
  • 5,652
  • 2
  • 34
  • 34
-3

To disable warning from third-party header file, add following line at the top of file

#pragma clang system_header
harvestli
  • 15
  • 1
  • 3