<html><head><meta http-equiv="Content-Type" content="text/html; charset=us-ascii"></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; line-break: after-white-space;" class=""><br class=""><div><br class=""><blockquote type="cite" class=""><div class="">On Oct 18, 2017, at 6:05 PM, Thibault Wittemberg via swift-dev &lt;<a href="mailto:swift-dev@swift.org" class="">swift-dev@swift.org</a>&gt; wrote:</div><br class="Apple-interchange-newline"><div class=""><meta http-equiv="Content-Type" content="text/html; charset=us-ascii" class=""><div style="word-wrap: break-word; -webkit-nbsp-mode: space; line-break: after-white-space;" class=""><div class="">Hi everyone,</div><div class=""><br data-mce-bogus="1" class=""></div><div class="">I am a member of the RxSwiftCommunity, and I am facing an issue on a PR that I've made (<a href="https://github.com/RxSwiftCommunity/NSObject-Rx/pull/49" class="">https://github.com/RxSwiftCommunity/NSObject-Rx/pull/49</a>).</div><div class=""><br data-mce-bogus="1" class=""></div><div class="">The big picture is:</div><div class="">I have a protocol that declares a computed var (get set) with a default implementation that uses the "<b class=""><span class="pl-c1" data-mce-style="box-sizing: border-box; color: #005cc5; font-family: SFMono-Regular, Consolas, 'Liberation Mono', Menlo, Courier, monospace; font-size: 12px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; white-space: pre; widows: auto; word-spacing: 0px; -webkit-text-size-adjust: auto; -webkit-text-stroke-width: 0px;" style="box-sizing: border-box; color: rgb(0, 92, 197); font-family: SFMono-Regular, Consolas, &quot;Liberation Mono&quot;, Menlo, Courier, monospace; white-space: pre;">objc_setAssociatedObject</span><span data-mce-style="color: #24292e; font-family: SFMono-Regular, Consolas, 'Liberation Mono', Menlo, Courier, monospace; font-size: 12px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; white-space: pre; widows: auto; word-spacing: 0px; -webkit-text-size-adjust: auto; -webkit-text-stroke-width: 0px; background-color: #e6ffed; display: inline !important; float: none;" style="color: rgb(36, 41, 46); font-family: SFMono-Regular, Consolas, &quot;Liberation Mono&quot;, Menlo, Courier, monospace; white-space: pre; background-color: rgb(230, 255, 237); float: none; display: inline !important;" class="">(</span><span class="pl-c1" data-mce-style="box-sizing: border-box; color: #005cc5; font-family: SFMono-Regular, Consolas, 'Liberation Mono', Menlo, Courier, monospace; font-size: 12px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; white-space: pre; widows: auto; word-spacing: 0px; -webkit-text-size-adjust: auto; -webkit-text-stroke-width: 0px;" style="box-sizing: border-box; color: rgb(0, 92, 197); font-family: SFMono-Regular, Consolas, &quot;Liberation Mono&quot;, Menlo, Courier, monospace; white-space: pre;">self</span><span data-mce-style="color: #24292e; font-family: SFMono-Regular, Consolas, 'Liberation Mono', Menlo, Courier, monospace; font-size: 12px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; white-space: pre; widows: auto; word-spacing: 0px; -webkit-text-size-adjust: auto; -webkit-text-stroke-width: 0px; background-color: #e6ffed; display: inline !important; float: none;" style="color: rgb(36, 41, 46); font-family: SFMono-Regular, Consolas, &quot;Liberation Mono&quot;, Menlo, Courier, monospace; white-space: pre; background-color: rgb(230, 255, 237); float: none; display: inline !important;" class="">, </span><span class="pl-k" data-mce-style="box-sizing: border-box; color: #d73a49; font-family: SFMono-Regular, Consolas, 'Liberation Mono', Menlo, Courier, monospace; font-size: 12px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; white-space: pre; widows: auto; word-spacing: 0px; -webkit-text-size-adjust: auto; -webkit-text-stroke-width: 0px;" style="box-sizing: border-box; color: rgb(215, 58, 73); font-family: SFMono-Regular, Consolas, &quot;Liberation Mono&quot;, Menlo, Courier, monospace; white-space: pre;">&amp;</span><span data-mce-style="color: #24292e; font-family: SFMono-Regular, Consolas, 'Liberation Mono', Menlo, Courier, monospace; font-size: 12px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; white-space: pre; widows: auto; word-spacing: 0px; -webkit-text-size-adjust: auto; -webkit-text-stroke-width: 0px; background-color: #e6ffed; display: inline !important; float: none;" style="color: rgb(36, 41, 46); font-family: SFMono-Regular, Consolas, &quot;Liberation Mono&quot;, Menlo, Courier, monospace; white-space: pre; background-color: rgb(230, 255, 237); float: none; display: inline !important;" class="">disposeBagContext, disposeObject, .</span><span class="pl-smi" data-mce-style="box-sizing: border-box; color: #24292e; font-family: SFMono-Regular, Consolas, 'Liberation Mono', Menlo, Courier, monospace; font-size: 12px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; white-space: pre; widows: auto; word-spacing: 0px; -webkit-text-size-adjust: auto; -webkit-text-stroke-width: 0px;" style="box-sizing: border-box; color: rgb(36, 41, 46); font-family: SFMono-Regular, Consolas, &quot;Liberation Mono&quot;, Menlo, Courier, monospace; white-space: pre;">OBJC_ASSOCIATION_RETAIN_NONATOMIC</span><span data-mce-style="color: #24292e; font-family: SFMono-Regular, Consolas, 'Liberation Mono', Menlo, Courier, monospace; font-size: 12px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; white-space: pre; widows: auto; word-spacing: 0px; -webkit-text-size-adjust: auto; -webkit-text-stroke-width: 0px; background-color: #e6ffed; display: inline !important; float: none;" style="color: rgb(36, 41, 46); font-family: SFMono-Regular, Consolas, &quot;Liberation Mono&quot;, Menlo, Courier, monospace; white-space: pre; background-color: rgb(230, 255, 237); float: none; display: inline !important;" class="">)</span></b>" primitive to store and retrieve its value.</div><div class="">Here is the complete code:</div><div class=""><pre data-mce-style="color: #000000; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; widows: auto; word-spacing: 0px; -webkit-text-size-adjust: auto; -webkit-text-stroke-width: 0px; word-wrap: break-word; white-space: pre-wrap;" style="word-wrap: break-word; white-space: pre-wrap;" class=""><span data-mce-style="font-size: 12px;" class="">public protocol HasDisposeBag {
    /// a unique RxSwift DisposeBag instance
    var disposeBag: DisposeBag { get set }
}
extension HasDisposeBag {
    func synchronizedBag&lt;T&gt;( _ action: () -&gt; T) -&gt; T {
        objc_sync_enter(self)
        let result = action()
        objc_sync_exit(self)
        return result
    }
    <span data-mce-style="color: #ff2968;" style="color: rgb(255, 41, 104);" class="">public var disposeBag: DisposeBag {
        get {
            return synchronizedBag {
                if let disposeObject = objc_getAssociatedObject(self, &amp;disposeBagContext) as? DisposeBag {
                    return disposeObject
                }
                let disposeObject = DisposeBag()
                objc_setAssociatedObject(self, &amp;disposeBagContext, disposeObject, .OBJC_ASSOCIATION_RETAIN_NONATOMIC)
                return disposeObject
            }
        }
        set {
            synchronizedBag {
                objc_setAssociatedObject(self, &amp;disposeBagContext, newValue, .OBJC_ASSOCIATION_RETAIN_NONATOMIC)
            }
        }
    }</span>
}</span></pre></div><div class=""><br data-mce-bogus="1" class=""></div><div class="">The question is: what happens when it is a struct that conforms to this protocol ?</div></div></div></blockquote><div><br class=""></div>Nothing good. It is unsafe to use objc_setAssociatedObject() with a Swift struct. For that matter you can't use objc_sync_enter/exit either.</div><div><br class=""></div><div><br class=""></div><div>--&nbsp;</div><div>Greg Parker &nbsp; &nbsp; <a href="mailto:gparker@apple.com" class="">gparker@apple.com</a> &nbsp; &nbsp; Runtime Wrangler</div><div><br class=""></div><div><br class=""></div></body></html>