[cfe-dev] Proposal: Add a runtime availability check feature to Objective-C, C

Nico Weber via cfe-dev cfe-dev at lists.llvm.org
Mon Jul 11 11:52:48 PDT 2016


Hi Erik,

this sounds very useful, thanks for working on it. One think Ted had
suggested on the review for r232750 (that I failed to follow up on :-/) was
to also have a #pragma to mark whole regions as e.g. 10.10+. From
https://www.mail-archive.com/cfe-commits@cs.uiuc.edu/msg117130.html:

  #pragma clang assume_availability(macosx, 10.8) begin
  ...
  #pragma clang assume_availability(macosx, 10.8) end

Is this something you'll look at as well?

Nico

On Tue, Jul 5, 2016 at 2:59 PM, Erik Pilkington via cfe-dev <
cfe-dev at lists.llvm.org> wrote:

> Hello,
>
> I'm an intern at Apple this summer, and my project is to add the following
> feature to C and Objective-C.
>
> The feature in question is adding the ability to safely access APIs that
> are
> only available in some of the deployment targets available, based on the
> availability attribute that the declarations were declared with.
>
> Swift has an analogous feature exposed through the following syntax:
>
>   if #available(iOS 8, *) {
>     // do something iOS8-ey
>   }
>
> In the context of the body of the `if`, accesses to declarations that are
> marked
> as being available in iOS version 8 or below can be accessed safely and
> without
> compiler errors, even if the deployment target is iOS 7, for example.
> Outside of
> that block, accessing the declarations would be a hard error.
>
> Currently, Clang exposes no safe way to perform a similar check. Right now,
> there are 2 main methods for checking for availability in Objective-C:
>
>   1. Using respondsToSelector
>   2. Checking if a weak symbol is NULL
>
> There are two main problems with these methods. Firstly, they allow
> programmers
> to accidentally use SPIs ("Secret" Programming Interface, aka internal
> stuff),
> ignoring that they are marked as being unavailable to them. Secondly, we
> cannot
> use them for diagnostics in all cases, as they can be combined with
> arbitrary
> control flow. If we were to infer the availability of a declaration based
> on
> these existing checks, then code would be fragile — a small change that
> doesn’t
> alter the semantics of the function could cause the compiler to become
> confused
> and incorrectly handle diagnostics.
>
> There also does exist a -Wpartial-availability (introduced in r232750),
> which
> just statically compares the deployment target with the marked
> availability of
> the API, potentially warning if necessary. This doesn't allow using a
> newer API
> with an older deployment target, as this feature does.
>
> My proposal is to implement a similar feature to Swift for C and
> Objective-C.
> The current syntax (subject to change) is as follows:
>
>   if (@available(macos 10.10, *)) {
>     fancy_new_fn();
>   }
>
> And the following for C and C++:
>
>   if (__builtin_available(macos 10.10, *)) {
>     fancy_new_fn();
>   }
>
> And would have similar semantics to the swift version discussed above,
> meaning
> it would compile to a runtime check of the availability, branching on the
> result. In the body of the if, the deployment target would effectively be
> the
> target in the @available check. This means that any declaration that is
> marked
> with an `__attribute__((availability))` which was introduced before or at
> MacOS
> 10.10 can be accessed in the block. Here is a complete example:
>
>   void flashy_new_function() __attribute__((availability(macosx,
> introduced=10.10)));
>   void boring_old_function() __attribute__((availability(macosx,
> introduced=10.9)));
>
>   int main() {
>     if (@available(macos 10.10, *))
>       flashy_new_function();
>     else
>       boring_old_function();
>   }
>
> And compiled with:
>
>   $ clang example.m -mmacos-version-min=10.9
>
> In this case, since the call to fancy_new_function() is guarded by the
> runtime
> check, clang would emit no warnings. If main were instead:
>
>   int main() {
>     flashy_new_function();
>   }
>
> Then clang will warn that the call is unsafe. Additionally, Clang will
> emit a
> fixit that could wrap the call to flashy_new_function in an @available (or
> __builtin_available, when needed) check.
>
> I would appreciate hearing any thoughts or questions about this feature.
>
> Cheers,
> Erik Pilkington
>
> _______________________________________________
> cfe-dev mailing list
> cfe-dev at lists.llvm.org
> http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-dev
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-dev/attachments/20160711/2517bc9b/attachment.html>


More information about the cfe-dev mailing list