<html><head><meta http-equiv="Content-Type" content="text/html charset=us-ascii"></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;" class=""><br class=""><div><blockquote type="cite" class=""><div class="">On Feb 10, 2016, at 7:57 PM, Jordan Rose &lt;<a href="mailto:jordan_rose@apple.com" class="">jordan_rose@apple.com</a>&gt; wrote:</div><div class=""><meta http-equiv="Content-Type" content="text/html charset=us-ascii" class=""><div style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;" class=""><br class=""><div class=""><blockquote type="cite" class=""><div class="">On Feb 10, 2016, at 18:29 , Greg Parker &lt;<a href="mailto:gparker@apple.com" class="">gparker@apple.com</a>&gt; wrote:</div><div class=""><meta http-equiv="Content-Type" content="text/html charset=us-ascii" class=""><div style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;" class=""><br class=""><div class=""><blockquote type="cite" class=""><div class="">On Feb 10, 2016, at 5:45 PM, Jordan Rose via swift-evolution &lt;<a href="mailto:swift-evolution@swift.org" class="">swift-evolution@swift.org</a>&gt; wrote:</div><br class="Apple-interchange-newline"><div class=""><meta http-equiv="Content-Type" content="text/html charset=utf-8" class=""><div style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;" class="">Hey, everyone. Here's a small feature with ABI implications, ready for feedback. In addition to comments on the proposal itself, I'm also interested in hearing how often this comes up for people:<div class=""><br class=""></div><div class="">- extending a class you don't own</div><div class="">- to add an overridable method</div><div class="">- where some of the overriders might be outside the current module<br class=""><div class=""><br class=""></div><div class="">Jordan</div><div class=""><br class=""><div class=""><a href="https://github.com/jrose-apple/swift-evolution/blob/overridable-members-in-extensions/proposals/nnnn-overridable-members-in-extensions.md" class="">https://github.com/jrose-apple/swift-evolution/blob/overridable-members-in-extensions/proposals/nnnn-overridable-members-in-extensions.md</a><div class=""><br class=""></div></div></div></div><div class="">---</div><div class=""><br class=""></div><div class=""><h1 style="box-sizing: border-box; margin-right: 0px; margin-bottom: 16px; margin-left: 0px; line-height: 1.2; padding-bottom: 0.3em; border-bottom-width: 1px; border-bottom-style: solid; border-bottom-color: rgb(238, 238, 238); color: rgb(51, 51, 51); font-family: 'Helvetica Neue', Helvetica, 'Segoe UI', Arial, freesans, sans-serif, 'Apple Color Emoji', 'Segoe UI Emoji', 'Segoe UI Symbol'; background-color: rgb(255, 255, 255); margin-top: 0px !important; font-size: 25px;" class="">Overridable Members in Extensions</h1><ul style="box-sizing: border-box; padding: 0px 0px 0px 2em; margin-top: 0px; margin-bottom: 16px; color: rgb(51, 51, 51); font-family: 'Helvetica Neue', Helvetica, 'Segoe UI', Arial, freesans, sans-serif, 'Apple Color Emoji', 'Segoe UI Emoji', 'Segoe UI Symbol'; background-color: rgb(255, 255, 255); font-size: 14px;" class=""><li style="box-sizing: border-box;" class=""><a id="user-content-library-evolution" class="anchor" href="https://github.com/jrose-apple/swift-evolution/tree/overridable-members-in-extensions#library-evolution" aria-hidden="true" style="font-size: 16px; box-sizing: border-box; color: rgb(64, 120, 192); text-decoration: none; display: inline-block; padding-right: 2px; margin-left: -18px; line-height: 1.2;"><svg aria-hidden="true" class="octicon octicon-link" height="16" role="img" version="1.1" viewBox="0 0 16 16" width="16"><path d="M4 9h1v1h-1c-1.5 0-3-1.69-3-3.5s1.55-3.5 3-3.5h4c1.45 0 3 1.69 3 3.5 0 1.41-0.91 2.72-2 3.25v-1.16c0.58-0.45 1-1.27 1-2.09 0-1.28-1.02-2.5-2-2.5H4c-0.98 0-2 1.22-2 2.5s1 2.5 2 2.5z m9-3h-1v1h1c1 0 2 1.22 2 2.5s-1.02 2.5-2 2.5H9c-0.98 0-2-1.22-2-2.5 0-0.83 0.42-1.64 1-2.09v-1.16c-1.09 0.53-2 1.84-2 3.25 0 1.81 1.55 3.5 3 3.5h4c1.45 0 3-1.69 3-3.5s-1.5-3.5-3-3.5z"></path></svg></a><span style="font-size: 16px;" class="">Library Evolution</span></li></ul><p style="box-sizing: border-box; margin-top: 0px; margin-bottom: 16px; color: rgb(51, 51, 51); font-family: 'Helvetica Neue', Helvetica, 'Segoe UI', Arial, freesans, sans-serif, 'Apple Color Emoji', 'Segoe UI Emoji', 'Segoe UI Symbol'; background-color: rgb(255, 255, 255); font-size: 14px;" class="">As with&nbsp;<a href="https://github.com/apple/swift/blob/master/docs/LibraryEvolution.rst#classes" style="box-sizing: border-box; background-color: transparent; color: rgb(64, 120, 192); text-decoration: none;" class="">any other method</a>, it is legal to "move" an extension method up to an extension on the base class, as long as the original declaration is not removed entirely. The new entry point will forward over to the original entry point in order to preserve binary compatibility.</p></div></div></div></blockquote><div class="">What happens if the base class adds an independent implementation of the same method?</div></div></div></div></blockquote><div class=""><br class=""></div><div class="">If it's an @objc method, you're hosed, just like you always were, but at least you'll (probably) find out when you recompile. I don't think there's anything we can do about this other than banning @objc methods in extensions, and I don't think that'll fly.</div><div class=""><br class=""></div><div class="">If it's a Swift method, it's not the "same" method; it's just another method with the same full-name. Existing binaries won't conflict. When you recompile, though, you'll get a conflict, and we don't currently have any annotations that allow you to <i class="">fix</i>&nbsp;that conflict, or for subclasses in a client module to deal with the intermediate module not yet having fixed the conflict. This isn't specific to extensions, though; you have the same problem with methods declared in the class body.</div></div></div></div></blockquote><div><br class=""></div>Good. I think that is the best result we can hope for here.<br class=""><br class=""><blockquote type="cite" class=""><div class=""><div style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;" class=""><div class=""><blockquote type="cite" class=""><div class=""><div style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;" class=""><div class=""><blockquote type="cite" class=""><div class=""><div style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;" class=""><div class=""><h2 style="box-sizing: border-box; margin-top: 1em; margin-bottom: 16px; line-height: 1.225; padding-bottom: 0.3em; border-bottom-width: 1px; border-bottom-style: solid; border-bottom-color: rgb(238, 238, 238); color: rgb(51, 51, 51); font-family: 'Helvetica Neue', Helvetica, 'Segoe UI', Arial, freesans, sans-serif, 'Apple Color Emoji', 'Segoe UI Emoji', 'Segoe UI Symbol'; background-color: rgb(255, 255, 255); font-size: 19px;" class=""></h2><h2 style="box-sizing: border-box; margin-top: 1em; margin-bottom: 16px; line-height: 1.225; padding-bottom: 0.3em; border-bottom-width: 1px; border-bottom-style: solid; border-bottom-color: rgb(238, 238, 238); color: rgb(51, 51, 51); font-family: 'Helvetica Neue', Helvetica, 'Segoe UI', Arial, freesans, sans-serif, 'Apple Color Emoji', 'Segoe UI Emoji', 'Segoe UI Symbol'; background-color: rgb(255, 255, 255); font-size: 19px;" class=""><a id="user-content-future-extensions" class="anchor" href="https://github.com/jrose-apple/swift-evolution/tree/overridable-members-in-extensions#future-extensions" aria-hidden="true" style="box-sizing: border-box; background-color: transparent; color: rgb(64, 120, 192); text-decoration: none; display: inline-block; padding-right: 2px; margin-left: -18px; line-height: 1;"><svg aria-hidden="true" class="octicon octicon-link" height="16" role="img" version="1.1" viewBox="0 0 16 16" width="16"><path d="M4 9h1v1h-1c-1.5 0-3-1.69-3-3.5s1.55-3.5 3-3.5h4c1.45 0 3 1.69 3 3.5 0 1.41-0.91 2.72-2 3.25v-1.16c0.58-0.45 1-1.27 1-2.09 0-1.28-1.02-2.5-2-2.5H4c-0.98 0-2 1.22-2 2.5s1 2.5 2 2.5z m9-3h-1v1h1c1 0 2 1.22 2 2.5s-1.02 2.5-2 2.5H9c-0.98 0-2-1.22-2-2.5 0-0.83 0.42-1.64 1-2.09v-1.16c-1.09 0.53-2 1.84-2 3.25 0 1.81 1.55 3.5 3 3.5h4c1.45 0 3-1.69 3-3.5s-1.5-3.5-3-3.5z"></path></svg></a>Future extensions</h2><p style="box-sizing: border-box; margin-top: 0px; margin-bottom: 16px; color: rgb(51, 51, 51); font-family: 'Helvetica Neue', Helvetica, 'Segoe UI', Arial, freesans, sans-serif, 'Apple Color Emoji', 'Segoe UI Emoji', 'Segoe UI Symbol'; background-color: rgb(255, 255, 255); font-size: 14px;" class="">The restriction that an extension cannot override a method from another module is intended for safety purposes, preventing two modules from each adding their own override. It's possible to make this a link-time failure rather than a compile-time failure by emitting a dummy symbol representing the (class, member) pair.</p></div></div></div></blockquote></div><div class="">Dummy symbol enforcement only helps when two conflicting modules have a linkage relationship (i.e. one links to the other). It won't catch the case where two independent modules collide.</div></div></div></blockquote><div class=""><br class=""></div><div class="">If two linker modules provide the same public symbol, that won't cause an issue?</div></div></div></div></blockquote><div><br class=""></div><div>No, at least not with OS X two-level symbol lookup. If some linkage unit tried to use that symbol and linked to two different providers of the symbol then you would get a link-time error. Otherwise there wouldn't be any link-time or load-time problems.</div><div><br class=""></div></div><div class=""><br class=""></div><div class="">--&nbsp;</div><div class="">Greg Parker &nbsp; &nbsp; <a href="mailto:gparker@apple.com" class="">gparker@apple.com</a> &nbsp; &nbsp; Runtime Wrangler</div><div class=""><br class=""></div><div class=""><br class=""></div></body></html>