Changeset 280952 in webkit
- Timestamp:
- Aug 11, 2021, 7:08:08 PM (5 years ago)
- Location:
- trunk/Source
- Files:
-
- 4 edited
-
WTF/ChangeLog (modified) (1 diff)
-
WTF/wtf/RetainPtr.h (modified) (13 diffs)
-
WebKit/ChangeLog (modified) (1 diff)
-
WebKit/UIProcess/mac/WKTextFinderClient.mm (modified) (1 diff)
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/WTF/ChangeLog
r280934 r280952 1 2021-08-11 Darin Adler <darin@apple.com> 2 3 Add deduction guide to RetainPtr, use constexpr a bit more, and streamline the implementation 4 https://bugs.webkit.org/show_bug.cgi?id=228852 5 6 Reviewed by Sam Weinig. 7 8 * wtf/RetainPtr.h: Sort includes. Made many functions constexpr including the move 9 constructors and adoptCF. Use using instead of typedef in most places. Use 10 remove_pointer_t, conditional_t, is_convertible_v, is_same_v, and other such templates 11 to simplify expressions. Initialize the m_ptr data member and use the default constructor. 12 Removed unneeded StorageType synonym for CFTypeRef. Move some inline function bodies out 13 of the class template definition. Use if constexpr to get rid of the need for the overloaded 14 autoreleaseHelper function. Added a deduction guide so we can use expressions with the 15 type RetainPtr on the left side, and an Objective-C pointer or CFTypeRef on the right side, 16 and have the appropriate RetainPtr type deduced. 17 1 18 2021-08-11 Sihui Liu <sihui_liu@apple.com> 2 19 -
trunk/Source/WTF/wtf/RetainPtr.h
r275650 r280952 1 1 /* 2 * Copyright (C) 2005-20 19Apple Inc. All rights reserved.2 * Copyright (C) 2005-2021 Apple Inc. All rights reserved. 3 3 * 4 4 * This library is free software; you can redistribute it and/or … … 25 25 #if USE(CF) || defined(__OBJC__) 26 26 27 #include <wtf/HashTraits.h>28 27 #include <algorithm> 29 28 #include <cstddef> 29 #include <wtf/HashTraits.h> 30 #include <wtf/NeverDestroyed.h> 30 31 31 32 #if USE(CF) … … 66 67 template<typename T> class RetainPtr; 67 68 68 template<typename T> RetainPtr<T> adoptCF(T CF_RELEASES_ARGUMENT) WARN_UNUSED_RETURN; 69 template<typename T> constexpr RetainPtr<T> adoptCF(T CF_RELEASES_ARGUMENT) WARN_UNUSED_RETURN; 70 69 71 #ifdef __OBJC__ 70 72 template<typename T> RetainPtr<typename RetainPtr<T>::HelperPtrType> adoptNS(T NS_RELEASES_ARGUMENT) WARN_UNUSED_RETURN; … … 73 75 template<typename T> class RetainPtr { 74 76 public: 75 typedef typename std::remove_pointer<T>::type ValueType; 76 typedef ValueType* PtrType; 77 typedef CFTypeRef StorageType; 78 79 #ifdef __OBJC__ 80 typedef typename std::conditional<std::is_convertible<T, id>::value && !std::is_same<T, id>::value, typename std::remove_pointer<T>::type, T>::type HelperPtrType; 77 using ValueType = std::remove_pointer_t<T>; 78 using PtrType = ValueType*; 79 80 #ifdef __OBJC__ 81 using HelperPtrType = typename std::conditional_t<std::is_convertible_v<T, id> && !std::is_same_v<T, id>, std::remove_pointer_t<T>, T>; 81 82 #else 82 typedef T HelperPtrType; 83 #endif 84 85 RetainPtr() : m_ptr(nullptr) { } 86 RetainPtr(PtrType ptr) : m_ptr(toStorageType(ptr)) { if (m_ptr) CFRetain(m_ptr); } 87 88 RetainPtr(const RetainPtr& o) : m_ptr(o.m_ptr) { if (StorageType ptr = m_ptr) CFRetain(ptr); } 89 90 RetainPtr(RetainPtr&& o) : m_ptr(toStorageType(o.leakRef())) { } 91 template<typename U> RetainPtr(RetainPtr<U>&& o) : m_ptr(toStorageType(o.leakRef())) { } 83 using HelperPtrType = PtrType; 84 #endif 85 86 RetainPtr() = default; 87 RetainPtr(PtrType); 88 89 RetainPtr(const RetainPtr&); 90 template<typename U> RetainPtr(const RetainPtr<U>&); 91 92 constexpr RetainPtr(RetainPtr&& o) : m_ptr(toStorageType(o.leakRef())) { } 93 template<typename U> constexpr RetainPtr(RetainPtr<U>&& o) : m_ptr(toStorageType(o.leakRef())) { } 92 94 93 95 // Hash table deleted values, which are only constructed and never copied or destroyed. 94 RetainPtr(HashTableDeletedValueType) : m_ptr(hashTableDeletedValue()) { }95 bool isHashTableDeletedValue() const { return m_ptr == hashTableDeletedValue(); }96 96 constexpr RetainPtr(HashTableDeletedValueType) : m_ptr(hashTableDeletedValue()) { } 97 constexpr bool isHashTableDeletedValue() const { return m_ptr == hashTableDeletedValue(); } 98 97 99 ~RetainPtr(); 98 99 template<typename U> RetainPtr(const RetainPtr<U>&);100 100 101 101 void clear(); 102 102 PtrType leakRef() WARN_UNUSED_RETURN; 103 103 PtrType autorelease(); 104 104 105 #ifdef __OBJC__ 105 106 id bridgingAutorelease(); 106 107 #endif 107 108 108 PtrType get() const { return fromStorageType(m_ptr); }109 PtrType operator->() const { return fromStorageType(m_ptr); }110 explicit operator PtrType() const { return fromStorageType(m_ptr); }111 explicit operator bool() const { return m_ptr; }112 113 bool operator!() const { return !m_ptr; }109 constexpr PtrType get() const { return fromStorageType(m_ptr); } 110 constexpr PtrType operator->() const { return fromStorageType(m_ptr); } 111 constexpr explicit operator PtrType() const { return fromStorageType(m_ptr); } 112 constexpr explicit operator bool() const { return m_ptr; } 113 114 constexpr bool operator!() const { return !m_ptr; } 114 115 115 116 // This conversion operator allows implicit conversion to bool but not to other integer types. 116 typedef StorageType RetainPtr::*UnspecifiedBoolType; 117 // FIXME: Eventually we should remove this; it's an outdated technique and less needed since we have explicit operator bool. 118 typedef CFTypeRef RetainPtr::*UnspecifiedBoolType; 117 119 operator UnspecifiedBoolType() const { return m_ptr ? &RetainPtr::m_ptr : nullptr; } 118 120 119 121 RetainPtr& operator=(const RetainPtr&); 120 122 template<typename U> RetainPtr& operator=(const RetainPtr<U>&); … … 127 129 void swap(RetainPtr&); 128 130 129 template<typename U> friend RetainPtr<U> adoptCF(U CF_RELEASES_ARGUMENT) WARN_UNUSED_RETURN; 131 template<typename U> friend constexpr RetainPtr<U> adoptCF(U CF_RELEASES_ARGUMENT) WARN_UNUSED_RETURN; 132 130 133 #ifdef __OBJC__ 131 134 template<typename U> friend RetainPtr<typename RetainPtr<U>::HelperPtrType> adoptNS(U NS_RELEASES_ARGUMENT) WARN_UNUSED_RETURN; … … 134 137 private: 135 138 enum AdoptTag { Adopt }; 136 RetainPtr(PtrType ptr, AdoptTag) : m_ptr(toStorageType(ptr)) { } 137 138 static PtrType hashTableDeletedValue() { return reinterpret_cast<PtrType>(-1); } 139 140 #ifdef __OBJC__ 141 template<typename U> 142 typename std::enable_if<std::is_convertible<U, id>::value, PtrType>::type 143 fromStorageTypeHelper(StorageType ptr) const 139 constexpr RetainPtr(PtrType ptr, AdoptTag) : m_ptr(toStorageType(ptr)) { } 140 141 static constexpr PtrType hashTableDeletedValue() { return reinterpret_cast<PtrType>(-1); } 142 143 #ifdef __OBJC__ 144 template<typename U> constexpr std::enable_if_t<std::is_convertible_v<U, id>, PtrType> fromStorageTypeHelper(CFTypeRef ptr) const 144 145 { 145 146 return (__bridge PtrType)const_cast<CF_BRIDGED_TYPE(id) void*>(ptr); 146 147 } 147 148 template<typename U> 149 typename std::enable_if<!std::is_convertible<U, id>::value, PtrType>::type 150 fromStorageTypeHelper(StorageType ptr) const 148 template<typename U> constexpr std::enable_if_t<!std::is_convertible_v<U, id>, PtrType> fromStorageTypeHelper(CFTypeRef ptr) const 151 149 { 152 150 return (PtrType)const_cast<CF_BRIDGED_TYPE(id) void*>(ptr); 153 151 } 154 155 PtrType fromStorageType(StorageType ptr) const { return fromStorageTypeHelper<PtrType>(ptr); } 156 StorageType toStorageType(id ptr) const { return (__bridge StorageType)ptr; } 157 StorageType toStorageType(CFTypeRef ptr) const { return (StorageType)ptr; } 152 constexpr PtrType fromStorageType(CFTypeRef ptr) const { return fromStorageTypeHelper<PtrType>(ptr); } 153 constexpr CFTypeRef toStorageType(id ptr) const { return (__bridge CFTypeRef)ptr; } 154 constexpr CFTypeRef toStorageType(CFTypeRef ptr) const { return (CFTypeRef)ptr; } 158 155 #else 159 PtrType fromStorageType(StorageTypeptr) const156 constexpr PtrType fromStorageType(CFTypeRef ptr) const 160 157 { 161 158 return (PtrType)const_cast<CF_BRIDGED_TYPE(id) void*>(ptr); 162 159 } 163 StorageType toStorageType(PtrType ptr) const { return (StorageType)ptr; } 164 #endif 165 166 #ifdef __OBJC__ 167 template<typename U> std::enable_if_t<std::is_convertible<U, id>::value, PtrType> autoreleaseHelper(); 168 template<typename U> std::enable_if_t<!std::is_convertible<U, id>::value, PtrType> autoreleaseHelper(); 169 #endif 170 171 StorageType m_ptr; 160 constexpr CFTypeRef toStorageType(PtrType ptr) const { return (CFTypeRef)ptr; } 161 #endif 162 163 CFTypeRef m_ptr { nullptr }; 172 164 }; 165 166 template<typename T> RetainPtr(T) -> RetainPtr<std::remove_pointer_t<T>>; 173 167 174 168 // Helper function for creating a RetainPtr using template argument deduction. … … 177 171 template<typename T> inline RetainPtr<T>::~RetainPtr() 178 172 { 179 if ( StorageTypeptr = std::exchange(m_ptr, nullptr))173 if (auto ptr = std::exchange(m_ptr, nullptr)) 180 174 CFRelease(ptr); 181 175 } 182 176 177 template<typename T> inline RetainPtr<T>::RetainPtr(PtrType ptr) 178 : m_ptr(toStorageType(ptr)) 179 { 180 if (m_ptr) 181 CFRetain(m_ptr); 182 } 183 184 template<typename T> inline RetainPtr<T>::RetainPtr(const RetainPtr& o) 185 : RetainPtr(o.get()) 186 { 187 } 188 183 189 template<typename T> template<typename U> inline RetainPtr<T>::RetainPtr(const RetainPtr<U>& o) 184 : m_ptr(toStorageType(o.get())) 185 { 186 if (StorageType ptr = m_ptr) 187 CFRetain(ptr); 190 : RetainPtr(o.get()) 191 { 188 192 } 189 193 190 194 template<typename T> inline void RetainPtr<T>::clear() 191 195 { 192 if ( StorageTypeptr = std::exchange(m_ptr, nullptr))196 if (auto ptr = std::exchange(m_ptr, nullptr)) 193 197 CFRelease(ptr); 194 198 } … … 199 203 } 200 204 201 #ifndef __OBJC__202 203 205 template<typename T> inline auto RetainPtr<T>::autorelease() -> PtrType 204 206 { 207 #ifdef __OBJC__ 208 if constexpr (std::is_convertible_v<PtrType, id>) 209 return CFBridgingRelease(std::exchange(m_ptr, nullptr)); 210 #endif 205 211 if (m_ptr) 206 212 CFAutorelease(m_ptr); … … 208 214 } 209 215 210 #else 211 212 template<typename T> template<typename U> inline auto RetainPtr<T>::autoreleaseHelper() -> std::enable_if_t<std::is_convertible<U, id>::value, PtrType> 213 { 214 return CFBridgingRelease(std::exchange(m_ptr, nullptr)); 215 } 216 217 template<typename T> template<typename U> inline auto RetainPtr<T>::autoreleaseHelper() -> std::enable_if_t<!std::is_convertible<U, id>::value, PtrType> 218 { 219 if (m_ptr) 220 CFAutorelease(m_ptr); 221 return leakRef(); 222 } 223 224 template<typename T> inline auto RetainPtr<T>::autorelease() -> PtrType 225 { 226 return autoreleaseHelper<PtrType>(); 227 } 228 229 // FIXME: It would be nice if we could base the return type on the type that is toll-free bridged with T rather than using id. 216 #ifdef __OBJC__ 217 218 // FIXME: It would be better if we could base the return type on the type that is toll-free bridged with T rather than using id. 230 219 template<typename T> inline id RetainPtr<T>::bridgingAutorelease() 231 220 { … … 288 277 } 289 278 290 template<typename T, typename U> inlinebool operator==(const RetainPtr<T>& a, const RetainPtr<U>& b)279 template<typename T, typename U> constexpr bool operator==(const RetainPtr<T>& a, const RetainPtr<U>& b) 291 280 { 292 281 return a.get() == b.get(); 293 282 } 294 283 295 template<typename T, typename U> inlinebool operator==(const RetainPtr<T>& a, U* b)284 template<typename T, typename U> constexpr bool operator==(const RetainPtr<T>& a, U* b) 296 285 { 297 286 return a.get() == b; 298 287 } 299 288 300 template<typename T, typename U> inline bool operator==(T* a, const RetainPtr<U>& b)289 template<typename T, typename U> constexpr bool operator==(T* a, const RetainPtr<U>& b) 301 290 { 302 291 return a == b.get(); 303 292 } 304 293 305 template<typename T, typename U> inlinebool operator!=(const RetainPtr<T>& a, const RetainPtr<U>& b)294 template<typename T, typename U> constexpr bool operator!=(const RetainPtr<T>& a, const RetainPtr<U>& b) 306 295 { 307 296 return a.get() != b.get(); 308 297 } 309 298 310 template<typename T, typename U> inlinebool operator!=(const RetainPtr<T>& a, U* b)299 template<typename T, typename U> constexpr bool operator!=(const RetainPtr<T>& a, U* b) 311 300 { 312 301 return a.get() != b; 313 302 } 314 303 315 template<typename T, typename U> inlinebool operator!=(T* a, const RetainPtr<U>& b)304 template<typename T, typename U> constexpr bool operator!=(T* a, const RetainPtr<U>& b) 316 305 { 317 306 return a != b.get(); 318 307 } 319 308 320 template<typename T> inlineRetainPtr<T> adoptCF(T CF_RELEASES_ARGUMENT ptr)309 template<typename T> constexpr RetainPtr<T> adoptCF(T CF_RELEASES_ARGUMENT ptr) 321 310 { 322 311 #ifdef __OBJC__ … … 332 321 return ptr; 333 322 #elif defined(OBJC_NO_GC) 334 return RetainPtr<typename RetainPtr<T>::HelperPtrType>(ptr, RetainPtr<typename RetainPtr<T>::HelperPtrType>::Adopt); 323 using ReturnType = RetainPtr<typename RetainPtr<T>::HelperPtrType>; 324 return ReturnType { ptr, ReturnType::Adopt }; 335 325 #else 336 326 RetainPtr<typename RetainPtr<T>::HelperPtrType> result = ptr; … … 346 336 } 347 337 348 template <typename T> struct IsSmartPtr<RetainPtr<T>> {338 template<typename T> struct IsSmartPtr<RetainPtr<T>> { 349 339 static constexpr bool value = true; 350 340 }; … … 355 345 template<typename P> struct DefaultHash<RetainPtr<P>> : PtrHash<RetainPtr<P>> { }; 356 346 357 template <typename P> 358 struct RetainPtrObjectHashTraits : SimpleClassHashTraits<RetainPtr<P>> { 347 template<typename P> struct RetainPtrObjectHashTraits : SimpleClassHashTraits<RetainPtr<P>> { 359 348 static const RetainPtr<P>& emptyValue() 360 349 { 361 static RetainPtr<P>& null = *(new RetainPtr<P>);350 static NeverDestroyed<RetainPtr<P>> null; 362 351 return null; 363 352 } 364 353 }; 365 354 366 template <typename P> 367 struct RetainPtrObjectHash { 355 template<typename P> struct RetainPtrObjectHash { 368 356 static unsigned hash(const RetainPtr<P>& o) 369 357 { -
trunk/Source/WebKit/ChangeLog
r280951 r280952 1 2021-08-11 Darin Adler <darin@apple.com> 2 3 Add deduction guide to RetainPtr, use constexpr a bit more, and streamline the implementation 4 https://bugs.webkit.org/show_bug.cgi?id=228852 5 6 Reviewed by Sam Weinig. 7 8 * UIProcess/mac/WKTextFinderClient.mm: 9 (-[WKTextFinderClient findMatchesForString:relativeToMatch:findOptions:maxResults:resultCollector:]): 10 Test the deduction guide by writing RetainPtr instead of RetainPtr<NSProgress>. 11 1 12 2021-08-11 Peng Liu <peng.liu6@apple.com> 2 13 -
trunk/Source/WebKit/UIProcess/mac/WKTextFinderClient.mm
r272784 r280952 226 226 } 227 227 228 RetainPtr <NSProgress>progress = [NSProgress progressWithTotalUnitCount:1];228 RetainPtr progress = [NSProgress progressWithTotalUnitCount:1]; 229 229 auto copiedResultCollector = Block_copy(resultCollector); 230 230 _findReplyCallbacks.append([progress, copiedResultCollector] (NSArray *matches, bool didWrap) {
Note:
See TracChangeset
for help on using the changeset viewer.