From a9ad07a94506b8a6b144eae5bd38ae6e0795f58e Mon Sep 17 00:00:00 2001 From: Tom Poole Date: Thu, 25 Mar 2021 15:48:35 +0000 Subject: [PATCH] Use RAII for CFTypes --- .../native/juce_mac_CoreMidi.mm | 71 ++--- .../codecs/juce_CoreAudioFormat.cpp | 13 +- .../AU/juce_AU_Wrapper.mm | 21 +- .../VST/juce_VST_Wrapper.mm | 8 +- .../VST3/juce_VST3_Wrapper.cpp | 17 +- .../juce_AudioUnitPluginFormat.mm | 153 ++++------ .../format_types/juce_VST3PluginFormat.cpp | 44 +-- .../format_types/juce_VSTPluginFormat.cpp | 45 ++- .../juce_core/native/juce_mac_SystemStats.mm | 10 +- .../juce_core/native/juce_osx_ObjCHelpers.h | 57 ++-- .../native/juce_osx_MessageQueue.h | 13 +- .../native/juce_mac_CoreGraphicsContext.mm | 18 +- .../juce_graphics/native/juce_mac_Fonts.mm | 275 +++++++----------- .../native/juce_mac_IconHelpers.cpp | 34 +-- .../native/juce_ios_ContentSharer.cpp | 4 +- .../native/juce_ios_FileChooser.mm | 17 +- .../native/juce_mac_NSViewComponentPeer.mm | 8 +- .../native/juce_ios_PushNotifications.cpp | 4 +- .../native/juce_mac_AppleRemote.mm | 10 +- .../native/juce_mac_PushNotifications.cpp | 2 +- .../native/juce_mac_SystemTrayIcon.cpp | 8 +- .../juce_video/native/juce_ios_CameraDevice.h | 7 +- 22 files changed, 344 insertions(+), 495 deletions(-) diff --git a/modules/juce_audio_devices/native/juce_mac_CoreMidi.mm b/modules/juce_audio_devices/native/juce_mac_CoreMidi.mm index 49c8a60e5d..ba2b9611bd 100644 --- a/modules/juce_audio_devices/native/juce_mac_CoreMidi.mm +++ b/modules/juce_audio_devices/native/juce_mac_CoreMidi.mm @@ -414,10 +414,10 @@ namespace CoreMidiHelpers MidiDeviceInfo info; { - ScopedCFString str; + CFObjectHolder str; - if (CHECK_ERROR (MIDIObjectGetStringProperty (entity, kMIDIPropertyName, &str.cfString))) - info.name = String::fromCFString (str.cfString); + if (CHECK_ERROR (MIDIObjectGetStringProperty (entity, kMIDIPropertyName, &str.object))) + info.name = String::fromCFString (str.object); } SInt32 objectID = 0; @@ -428,10 +428,10 @@ namespace CoreMidiHelpers } else { - ScopedCFString str; + CFObjectHolder str; - if (CHECK_ERROR (MIDIObjectGetStringProperty (entity, kMIDIPropertyUniqueID, &str.cfString))) - info.identifier = String::fromCFString (str.cfString); + if (CHECK_ERROR (MIDIObjectGetStringProperty (entity, kMIDIPropertyUniqueID, &str.object))) + info.identifier = String::fromCFString (str.object); } return info; @@ -486,18 +486,18 @@ namespace CoreMidiHelpers MidiDeviceInfo result; // Does the endpoint have connections? - CFDataRef connections = nullptr; + CFObjectHolder connections; int numConnections = 0; - MIDIObjectGetDataProperty (endpoint, kMIDIPropertyConnectionUniqueID, &connections); + MIDIObjectGetDataProperty (endpoint, kMIDIPropertyConnectionUniqueID, &connections.object); - if (connections != nullptr) + if (connections.object != nullptr) { - numConnections = ((int) CFDataGetLength (connections)) / (int) sizeof (MIDIUniqueID); + numConnections = ((int) CFDataGetLength (connections.object)) / (int) sizeof (MIDIUniqueID); if (numConnections > 0) { - auto* pid = reinterpret_cast (CFDataGetBytePtr (connections)); + auto* pid = reinterpret_cast (CFDataGetBytePtr (connections.object)); for (int i = 0; i < numConnections; ++i, ++pid) { @@ -533,8 +533,6 @@ namespace CoreMidiHelpers } } } - - CFRelease (connections); } // Here, either the endpoint had no connections, or we failed to obtain names for them. @@ -552,24 +550,15 @@ namespace CoreMidiHelpers uniqueID = JUCE_STRINGIFY (JucePlugin_CFBundleIdentifier); #else auto appBundle = File::getSpecialLocation (File::currentApplicationFile); - ScopedCFString appBundlePath (appBundle.getFullPathName()); + CFUniquePtr appBundlePath (appBundle.getFullPathName().toCFString()); - if (auto bundleURL = CFURLCreateWithFileSystemPath (kCFAllocatorDefault, - appBundlePath.cfString, - kCFURLPOSIXPathStyle, - true)) - { - auto bundleRef = CFBundleCreate (kCFAllocatorDefault, bundleURL); - CFRelease (bundleURL); - - if (bundleRef != nullptr) - { - if (auto bundleId = CFBundleGetIdentifier (bundleRef)) + if (auto bundleURL = CFUniquePtr (CFURLCreateWithFileSystemPath (kCFAllocatorDefault, + appBundlePath.get(), + kCFURLPOSIXPathStyle, + true))) + if (auto bundleRef = CFUniquePtr (CFBundleCreate (kCFAllocatorDefault, bundleURL.get()))) + if (auto bundleId = CFBundleGetIdentifier (bundleRef.get())) uniqueID = String::fromCFString (bundleId); - - CFRelease (bundleRef); - } - } #endif if (uniqueID.isEmpty()) @@ -620,8 +609,8 @@ namespace CoreMidiHelpers enableSimulatorMidiSession(); - ScopedCFString name (getGlobalMidiClientName()); - CHECK_ERROR (MIDIClientCreate (name.cfString, &globalSystemChangeCallback, nullptr, &globalMidiClient)); + CFUniquePtr name (getGlobalMidiClientName().toCFString()); + CHECK_ERROR (MIDIClientCreate (name.get(), &globalSystemChangeCallback, nullptr, &globalMidiClient)); } return globalMidiClient; @@ -1058,16 +1047,16 @@ public: if (deviceIdentifier != endpointInfo.identifier) continue; - ScopedCFString cfName; + CFObjectHolder cfName; - if (! CHECK_ERROR (MIDIObjectGetStringProperty (endpoint, kMIDIPropertyName, &cfName.cfString))) + if (! CHECK_ERROR (MIDIObjectGetStringProperty (endpoint, kMIDIPropertyName, &cfName.object))) continue; if (auto input = makeInput (endpointInfo.name, endpointInfo.identifier, std::forward (args)...)) { MIDIPortRef port; - if (! CHECK_ERROR (CreatorFunctionsToUse::createInputPort (protocol, client, cfName.cfString, input->internal.get(), &port))) + if (! CHECK_ERROR (CreatorFunctionsToUse::createInputPort (protocol, client, cfName.object, input->internal.get(), &port))) continue; ScopedPortRef scopedPort { port }; @@ -1098,9 +1087,9 @@ public: if (auto input = makeInput (deviceName, String (deviceIdentifier), std::forward (args)...)) { MIDIEndpointRef endpoint; - ScopedCFString name (deviceName); + CFUniquePtr name (deviceName.toCFString()); - auto err = CreatorFunctionsToUse::createDestination (protocol, client, name.cfString, input->internal.get(), &endpoint); + auto err = CreatorFunctionsToUse::createDestination (protocol, client, name.get(), input->internal.get(), &endpoint); ScopedEndpointRef scopedEndpoint { endpoint }; #if JUCE_IOS @@ -1228,14 +1217,14 @@ std::unique_ptr MidiOutput::openDevice (const String& deviceIdentifi if (deviceIdentifier != endpointInfo.identifier) continue; - ScopedCFString cfName; + CFObjectHolder cfName; - if (! CHECK_ERROR (MIDIObjectGetStringProperty (endpoint, kMIDIPropertyName, &cfName.cfString))) + if (! CHECK_ERROR (MIDIObjectGetStringProperty (endpoint, kMIDIPropertyName, &cfName.object))) continue; MIDIPortRef port; - if (! CHECK_ERROR (MIDIOutputPortCreate (client, cfName.cfString, &port))) + if (! CHECK_ERROR (MIDIOutputPortCreate (client, cfName.object, &port))) continue; ScopedPortRef scopedPort { port }; @@ -1258,9 +1247,9 @@ std::unique_ptr MidiOutput::createNewDevice (const String& deviceNam { MIDIEndpointRef endpoint; - ScopedCFString name (deviceName); + CFUniquePtr name (deviceName.toCFString()); - auto err = CreatorFunctionsToUse::createSource (ump::PacketProtocol::MIDI_1_0, client, name.cfString, &endpoint); + auto err = CreatorFunctionsToUse::createSource (ump::PacketProtocol::MIDI_1_0, client, name.get(), &endpoint); ScopedEndpointRef scopedEndpoint { endpoint }; #if JUCE_IOS diff --git a/modules/juce_audio_formats/codecs/juce_CoreAudioFormat.cpp b/modules/juce_audio_formats/codecs/juce_CoreAudioFormat.cpp index 8c60ed28a4..944c175aac 100644 --- a/modules/juce_audio_formats/codecs/juce_CoreAudioFormat.cpp +++ b/modules/juce_audio_formats/codecs/juce_CoreAudioFormat.cpp @@ -26,6 +26,7 @@ #if JUCE_MAC || JUCE_IOS #include +#include namespace juce { @@ -38,17 +39,15 @@ namespace StringArray findFileExtensionsForCoreAudioCodecs() { StringArray extensionsArray; - CFArrayRef extensions = nullptr; - UInt32 sizeOfArray = sizeof (extensions); + CFObjectHolder extensions; + UInt32 sizeOfArray = sizeof (extensions.object); - if (AudioFileGetGlobalInfo (kAudioFileGlobalInfo_AllExtensions, 0, nullptr, &sizeOfArray, &extensions) == noErr) + if (AudioFileGetGlobalInfo (kAudioFileGlobalInfo_AllExtensions, 0, nullptr, &sizeOfArray, &extensions.object) == noErr) { - auto numValues = CFArrayGetCount (extensions); + auto numValues = CFArrayGetCount (extensions.object); for (CFIndex i = 0; i < numValues; ++i) - extensionsArray.add ("." + String::fromCFString ((CFStringRef) CFArrayGetValueAtIndex (extensions, i))); - - CFRelease (extensions); + extensionsArray.add ("." + String::fromCFString ((CFStringRef) CFArrayGetValueAtIndex (extensions.object, i))); } return extensionsArray; diff --git a/modules/juce_audio_plugin_client/AU/juce_AU_Wrapper.mm b/modules/juce_audio_plugin_client/AU/juce_AU_Wrapper.mm index 0777e8c810..a329eb6ed6 100644 --- a/modules/juce_audio_plugin_client/AU/juce_AU_Wrapper.mm +++ b/modules/juce_audio_plugin_client/AU/juce_AU_Wrapper.mm @@ -719,12 +719,9 @@ public: if (state.getSize() > 0) { - CFDataRef ourState = CFDataCreate (kCFAllocatorDefault, (const UInt8*) state.getData(), (CFIndex) state.getSize()); - - CFStringRef key = CFStringCreateWithCString (kCFAllocatorDefault, JUCE_STATE_DICTIONARY_KEY, kCFStringEncodingUTF8); - CFDictionarySetValue (dict, key, ourState); - CFRelease (key); - CFRelease (ourState); + CFUniquePtr ourState (CFDataCreate (kCFAllocatorDefault, (const UInt8*) state.getData(), (CFIndex) state.getSize())); + CFUniquePtr key (CFStringCreateWithCString (kCFAllocatorDefault, JUCE_STATE_DICTIONARY_KEY, kCFStringEncodingUTF8)); + CFDictionarySetValue (dict, key.get(), ourState.get()); } } @@ -735,10 +732,9 @@ public: { { // Remove the data entry from the state to prevent the superclass loading the parameters - CFMutableDictionaryRef copyWithoutData = CFDictionaryCreateMutableCopy (nullptr, 0, (CFDictionaryRef) inData); - CFDictionaryRemoveValue (copyWithoutData, CFSTR (kAUPresetDataKey)); - ComponentResult err = MusicDeviceBase::RestoreState (copyWithoutData); - CFRelease (copyWithoutData); + CFUniquePtr copyWithoutData (CFDictionaryCreateMutableCopy (nullptr, 0, (CFDictionaryRef) inData)); + CFDictionaryRemoveValue (copyWithoutData.get(), CFSTR (kAUPresetDataKey)); + ComponentResult err = MusicDeviceBase::RestoreState (copyWithoutData.get()); if (err != noErr) return err; @@ -749,10 +745,9 @@ public: CFDictionaryRef dict = (CFDictionaryRef) inData; CFDataRef data = nullptr; - CFStringRef key = CFStringCreateWithCString (kCFAllocatorDefault, JUCE_STATE_DICTIONARY_KEY, kCFStringEncodingUTF8); + CFUniquePtr key (CFStringCreateWithCString (kCFAllocatorDefault, JUCE_STATE_DICTIONARY_KEY, kCFStringEncodingUTF8)); - bool valuePresent = CFDictionaryGetValueIfPresent (dict, key, (const void**) &data); - CFRelease (key); + bool valuePresent = CFDictionaryGetValueIfPresent (dict, key.get(), (const void**) &data); if (valuePresent) { diff --git a/modules/juce_audio_plugin_client/VST/juce_VST_Wrapper.mm b/modules/juce_audio_plugin_client/VST/juce_VST_Wrapper.mm index 7c4887e75e..92944250a3 100644 --- a/modules/juce_audio_plugin_client/VST/juce_VST_Wrapper.mm +++ b/modules/juce_audio_plugin_client/VST/juce_VST_Wrapper.mm @@ -202,11 +202,11 @@ void detachComponentFromWindowRefVST (Component* comp, void* window, bool isNSVi removeWindowHidingHooks (comp); - HIViewRef dummyView = (HIViewRef) (void*) (pointer_sized_int) - comp->getProperties() ["dummyViewRef"].toString().getHexValue64(); + CFUniquePtr dummyView ((HIViewRef) (void*) (pointer_sized_int) + comp->getProperties() ["dummyViewRef"].toString().getHexValue64()); - if (HIViewIsValid (dummyView)) - CFRelease (dummyView); + if (HIViewIsValid (dummyView.get())) + dummyView = nullptr; NSWindow* hostWindow = (NSWindow*) window; NSView* pluginView = (NSView*) comp->getWindowHandle(); diff --git a/modules/juce_audio_plugin_client/VST3/juce_VST3_Wrapper.cpp b/modules/juce_audio_plugin_client/VST3/juce_VST3_Wrapper.cpp index f76338a6f6..cb659ae9a9 100644 --- a/modules/juce_audio_plugin_client/VST3/juce_VST3_Wrapper.cpp +++ b/modules/juce_audio_plugin_client/VST3/juce_VST3_Wrapper.cpp @@ -23,17 +23,17 @@ ============================================================================== */ +#if JucePlugin_Build_VST3 && (JUCE_MAC || JUCE_WINDOWS || JUCE_LINUX) + #include #include -//============================================================================== -#if JucePlugin_Build_VST3 && (JUCE_MAC || JUCE_WINDOWS || JUCE_LINUX) +#if JUCE_MAC + #include + #include +#endif #if JUCE_PLUGINHOST_VST3 - #if JUCE_MAC - #include - #endif - #undef JUCE_VST3HEADERS_INCLUDE_HEADERS_ONLY #define JUCE_VST3HEADERS_INCLUDE_HEADERS_ONLY 1 #endif @@ -3131,9 +3131,8 @@ bool shutdownModule() globalBundleInstance = ref; moduleHandle = ref; - CFURLRef tempURL = CFBundleCopyBundleURL (ref); - CFURLGetFileSystemRepresentation (tempURL, true, (UInt8*) modulePath, MaxPathLength); - CFRelease (tempURL); + CFUniquePtr tempURL (CFBundleCopyBundleURL (ref)); + CFURLGetFileSystemRepresentation (tempURL.get(), true, (UInt8*) modulePath, MaxPathLength); } } diff --git a/modules/juce_audio_processors/format_types/juce_AudioUnitPluginFormat.mm b/modules/juce_audio_processors/format_types/juce_AudioUnitPluginFormat.mm index b70c067a08..f303b3b82e 100644 --- a/modules/juce_audio_processors/format_types/juce_AudioUnitPluginFormat.mm +++ b/modules/juce_audio_processors/format_types/juce_AudioUnitPluginFormat.mm @@ -127,12 +127,10 @@ namespace AudioUnitFormatHelpers static void getNameAndManufacturer (AudioComponent comp, String& name, String& manufacturer) { - CFStringRef cfName; - if (AudioComponentCopyName (comp, &cfName) == noErr) - { - name = String::fromCFString (cfName); - CFRelease (cfName); - } + CFObjectHolder cfName; + + if (AudioComponentCopyName (comp, &cfName.object) == noErr) + name = String::fromCFString (cfName.object); if (name.containsChar (':')) { @@ -206,15 +204,12 @@ namespace AudioUnitFormatHelpers const char* const utf8 = fileOrIdentifier.toUTF8(); - if (CFURLRef url = CFURLCreateFromFileSystemRepresentation (nullptr, (const UInt8*) utf8, - (CFIndex) strlen (utf8), file.isDirectory())) + if (auto url = CFUniquePtr (CFURLCreateFromFileSystemRepresentation (nullptr, (const UInt8*) utf8, + (CFIndex) strlen (utf8), file.isDirectory()))) { - CFBundleRef bundleRef = CFBundleCreate (kCFAllocatorDefault, url); - CFRelease (url); - - if (bundleRef != nullptr) + if (auto bundleRef = CFUniquePtr (CFBundleCreate (kCFAllocatorDefault, url.get()))) { - CFTypeRef bundleName = CFBundleGetValueForInfoDictionaryKey (bundleRef, CFSTR("CFBundleName")); + CFTypeRef bundleName = CFBundleGetValueForInfoDictionaryKey (bundleRef.get(), CFSTR("CFBundleName")); if (bundleName != nullptr && CFGetTypeID (bundleName) == CFStringGetTypeID()) name = String::fromCFString ((CFStringRef) bundleName); @@ -222,17 +217,17 @@ namespace AudioUnitFormatHelpers if (name.isEmpty()) name = file.getFileNameWithoutExtension(); - CFTypeRef versionString = CFBundleGetValueForInfoDictionaryKey (bundleRef, CFSTR("CFBundleVersion")); + CFTypeRef versionString = CFBundleGetValueForInfoDictionaryKey (bundleRef.get(), CFSTR("CFBundleVersion")); if (versionString != nullptr && CFGetTypeID (versionString) == CFStringGetTypeID()) version = String::fromCFString ((CFStringRef) versionString); - CFTypeRef manuString = CFBundleGetValueForInfoDictionaryKey (bundleRef, CFSTR("CFBundleGetInfoString")); + CFTypeRef manuString = CFBundleGetValueForInfoDictionaryKey (bundleRef.get(), CFSTR("CFBundleGetInfoString")); if (manuString != nullptr && CFGetTypeID (manuString) == CFStringGetTypeID()) manufacturer = String::fromCFString ((CFStringRef) manuString); - const ResFileRefNum resFileId = CFBundleOpenBundleResourceMap (bundleRef); + const ResFileRefNum resFileId = CFBundleOpenBundleResourceMap (bundleRef.get()); UseResFile (resFileId); const OSType thngType = stringToOSType ("thng"); @@ -285,8 +280,7 @@ namespace AudioUnitFormatHelpers [bundle release]; } - CFBundleCloseBundleResourceMap (bundleRef, resFileId); - CFRelease (bundleRef); + CFBundleCloseBundleResourceMap (bundleRef.get(), resFileId); } } @@ -444,23 +438,21 @@ public: { if (auto* au = pluginInstance.audioUnit) { - AudioUnitParameterValueFromString valueString; - valueString.inParamID = paramID; - - ScopedCFString cfInString (text); - valueString.inString = cfInString.cfString; - - UInt32 propertySize = sizeof (valueString); + AudioUnitParameterValueFromString pvfs; + pvfs.inParamID = paramID; + CFUniquePtr cfString (text.toCFString()); + pvfs.inString = cfString.get(); + UInt32 propertySize = sizeof (pvfs); auto err = AudioUnitGetProperty (au, kAudioUnitProperty_ParameterValueFromString, kAudioUnitScope_Global, 0, - &valueString, + &pvfs, &propertySize); if (! err) - return normaliseParamValue (valueString.outValue); + return normaliseParamValue (pvfs.outValue); } } @@ -1213,31 +1205,31 @@ public: } //============================================================================== - struct ScopedFactoryPresets + class ScopedFactoryPresets { + public: ScopedFactoryPresets (AudioUnit& au) { UInt32 sz = sizeof (CFArrayRef); - AudioUnitGetProperty (au, kAudioUnitProperty_FactoryPresets, - kAudioUnitScope_Global, 0, &presets, &sz); + kAudioUnitScope_Global, 0, &presets.object, &sz); } - ~ScopedFactoryPresets() + CFArrayRef get() const noexcept { - if (presets != nullptr) - CFRelease (presets); + return presets.object; } - CFArrayRef presets = nullptr; + private: + CFObjectHolder presets; }; int getNumPrograms() override { ScopedFactoryPresets factoryPresets { audioUnit }; - if (factoryPresets.presets != nullptr) - return (int) CFArrayGetCount (factoryPresets.presets); + if (factoryPresets.get() != nullptr) + return (int) CFArrayGetCount (factoryPresets.get()); return 0; } @@ -1258,13 +1250,13 @@ public: { ScopedFactoryPresets factoryPresets { audioUnit }; - if (factoryPresets.presets != nullptr - && newIndex < (int) CFArrayGetCount (factoryPresets.presets)) + if (factoryPresets.get() != nullptr + && newIndex < (int) CFArrayGetCount (factoryPresets.get())) { AUPreset current; current.presetNumber = newIndex; - if (auto* p = static_cast (CFArrayGetValueAtIndex (factoryPresets.presets, newIndex))) + if (auto* p = static_cast (CFArrayGetValueAtIndex (factoryPresets.get(), newIndex))) current.presetName = p->presetName; AudioUnitSetProperty (audioUnit, kAudioUnitProperty_PresentPreset, @@ -1292,10 +1284,10 @@ public: ScopedFactoryPresets factoryPresets { audioUnit }; - if (factoryPresets.presets != nullptr) + if (factoryPresets.get() != nullptr) { - for (CFIndex i = 0; i < CFArrayGetCount (factoryPresets.presets); ++i) - if (auto* p = static_cast (CFArrayGetValueAtIndex (factoryPresets.presets, i))) + for (CFIndex i = 0; i < CFArrayGetCount (factoryPresets.get()); ++i) + if (auto* p = static_cast (CFArrayGetValueAtIndex (factoryPresets.get(), i))) if (p->presetNumber == index) return String::fromCFString (p->presetName); } @@ -1313,11 +1305,9 @@ public: { if (properties.name.isNotEmpty()) { - CFStringRef contextName = properties.name.toCFString(); + CFObjectHolder contextName { properties.name.toCFString() }; AudioUnitSetProperty (audioUnit, kAudioUnitProperty_ContextName, kAudioUnitScope_Global, - 0, &contextName, sizeof (CFStringRef)); - - CFRelease (contextName); + 0, &contextName.object, sizeof (contextName.object)); } } @@ -1329,28 +1319,24 @@ public: void getCurrentProgramStateInformation (MemoryBlock& destData) override { - CFPropertyListRef propertyList = nullptr; - UInt32 sz = sizeof (CFPropertyListRef); + CFObjectHolder propertyList; + UInt32 sz = sizeof (propertyList.object); if (AudioUnitGetProperty (audioUnit, kAudioUnitProperty_ClassInfo, kAudioUnitScope_Global, - 0, &propertyList, &sz) == noErr) + 0, &propertyList.object, &sz) == noErr) { - CFWriteStreamRef stream = CFWriteStreamCreateWithAllocatedBuffers (kCFAllocatorDefault, kCFAllocatorDefault); - CFWriteStreamOpen (stream); + CFUniquePtr stream (CFWriteStreamCreateWithAllocatedBuffers (kCFAllocatorDefault, kCFAllocatorDefault)); + CFWriteStreamOpen (stream.get()); - CFIndex bytesWritten = CFPropertyListWriteToStream (propertyList, stream, kCFPropertyListBinaryFormat_v1_0, nullptr); - CFWriteStreamClose (stream); + CFIndex bytesWritten = CFPropertyListWriteToStream (propertyList.object, stream.get(), kCFPropertyListBinaryFormat_v1_0, nullptr); + CFWriteStreamClose (stream.get()); - CFDataRef data = (CFDataRef) CFWriteStreamCopyProperty (stream, kCFStreamPropertyDataWritten); + CFUniquePtr data ((CFDataRef) CFWriteStreamCopyProperty (stream.get(), kCFStreamPropertyDataWritten)); destData.setSize ((size_t) bytesWritten); - destData.copyFrom (CFDataGetBytePtr (data), 0, destData.getSize()); - CFRelease (data); - - CFRelease (stream); - CFRelease (propertyList); + destData.copyFrom (CFDataGetBytePtr (data.get()), 0, destData.getSize()); } } @@ -1361,23 +1347,20 @@ public: void setCurrentProgramStateInformation (const void* data, int sizeInBytes) override { - CFReadStreamRef stream = CFReadStreamCreateWithBytesNoCopy (kCFAllocatorDefault, (const UInt8*) data, - sizeInBytes, kCFAllocatorNull); - CFReadStreamOpen (stream); + CFUniquePtr stream (CFReadStreamCreateWithBytesNoCopy (kCFAllocatorDefault, (const UInt8*) data, + sizeInBytes, kCFAllocatorNull)); + CFReadStreamOpen (stream.get()); CFPropertyListFormat format = kCFPropertyListBinaryFormat_v1_0; - CFPropertyListRef propertyList = CFPropertyListCreateFromStream (kCFAllocatorDefault, stream, 0, - kCFPropertyListImmutable, &format, nullptr); - CFRelease (stream); + CFObjectHolder propertyList { CFPropertyListCreateFromStream (kCFAllocatorDefault, stream.get(), 0, + kCFPropertyListImmutable, &format, nullptr) }; - if (propertyList != nullptr) + if (propertyList.object != nullptr) { AudioUnitSetProperty (audioUnit, kAudioUnitProperty_ClassInfo, kAudioUnitScope_Global, - 0, &propertyList, sizeof (propertyList)); + 0, &propertyList.object, sizeof (propertyList.object)); sendAllParametersChangedEvents(); - - CFRelease (propertyList); } } @@ -2079,15 +2062,12 @@ private: busName = (isInput ? "Input #" : "Output #") + String (busIdx + 1); { - CFStringRef busNameCF = nullptr; - UInt32 propertySize = sizeof (busNameCF); + CFObjectHolder busNameCF; + UInt32 propertySize = sizeof (busNameCF.object); - if (AudioUnitGetProperty (comp, kAudioUnitProperty_ElementName, scope, static_cast (busIdx), &busNameCF, &propertySize) == noErr - && busNameCF != nullptr) - { - busName = nsStringToJuce ((NSString*) busNameCF); - CFRelease (busNameCF); - } + if (AudioUnitGetProperty (comp, kAudioUnitProperty_ElementName, scope, static_cast (busIdx), &busNameCF.object, &propertySize) == noErr) + if (busNameCF.object != nullptr) + busName = nsStringToJuce ((NSString*) busNameCF.object); { AudioChannelLayout auLayout; @@ -2221,21 +2201,15 @@ private: kAudioUnitScope_Global, 0, &dataSize, &isWritable) == noErr && dataSize != 0) { - CFArrayRef midiArray; + CFObjectHolder midiArray; if (AudioUnitGetProperty (audioUnit, kAudioUnitProperty_MIDIOutputCallbackInfo, - kAudioUnitScope_Global, 0, &midiArray, &dataSize) == noErr) - { - bool result = (CFArrayGetCount (midiArray) > 0); - CFRelease (midiArray); - return result; - } + kAudioUnitScope_Global, 0, &midiArray.object, &dataSize) == noErr) + return (CFArrayGetCount (midiArray.object) > 0); } + #endif return false; - #else - return false; - #endif } bool supportsMPE() const override @@ -2378,9 +2352,8 @@ private: 0, info, &dataSize) == noErr) { NSString* viewClassName = (NSString*) (info->mCocoaAUViewClass[0]); - CFStringRef path = CFURLCopyPath (info->mCocoaAUViewBundleLocation); - NSString* unescapedPath = (NSString*) CFURLCreateStringByReplacingPercentEscapes (nullptr, path, CFSTR ("")); - CFRelease (path); + CFUniquePtr path (CFURLCopyPath (info->mCocoaAUViewBundleLocation)); + NSString* unescapedPath = (NSString*) CFURLCreateStringByReplacingPercentEscapes (nullptr, path.get(), CFSTR ("")); NSBundle* viewBundle = [NSBundle bundleWithPath: [unescapedPath autorelease]]; Class viewClass = [viewBundle classNamed: viewClassName]; diff --git a/modules/juce_audio_processors/format_types/juce_VST3PluginFormat.cpp b/modules/juce_audio_processors/format_types/juce_VST3PluginFormat.cpp index 9161855f85..dd1bd72925 100644 --- a/modules/juce_audio_processors/format_types/juce_VST3PluginFormat.cpp +++ b/modules/juce_audio_processors/format_types/juce_VST3PluginFormat.cpp @@ -836,9 +836,6 @@ struct DLLHandle #if JUCE_WINDOWS || JUCE_LINUX library.close(); - #elif JUCE_MAC - CFRelease (bundleRef); - bundleRef = nullptr; #endif } } @@ -868,8 +865,8 @@ struct DLLHandle if (bundleRef == nullptr) return nullptr; - ScopedCFString name (functionName); - return CFBundleGetFunctionPointerForName (bundleRef, name.cfString); + CFUniquePtr name (String (functionName).toCFString()); + return CFBundleGetFunctionPointerForName (bundleRef.get(), name.get()); #endif } @@ -927,45 +924,32 @@ private: return false; } #elif JUCE_MAC - CFBundleRef bundleRef; + CFUniquePtr bundleRef; bool open() { auto* utf8 = dllFile.getFullPathName().toRawUTF8(); - if (CFURLRef url = CFURLCreateFromFileSystemRepresentation (nullptr, - (const UInt8*) utf8, - (CFIndex) std::strlen (utf8), - dllFile.isDirectory())) + if (auto url = CFUniquePtr (CFURLCreateFromFileSystemRepresentation (nullptr, + (const UInt8*) utf8, + (CFIndex) std::strlen (utf8), + dllFile.isDirectory()))) { - bundleRef = CFBundleCreate (kCFAllocatorDefault, url); - CFRelease (url); + bundleRef.reset (CFBundleCreate (kCFAllocatorDefault, url.get())); if (bundleRef != nullptr) { - CFErrorRef error = nullptr; + CFObjectHolder error; - if (CFBundleLoadExecutableAndReturnError (bundleRef, &error)) - { + if (CFBundleLoadExecutableAndReturnError (bundleRef.get(), &error.object)) if (auto* proc = (EntryProc) getFunction (entryFnName)) - { - if (proc (bundleRef)) + if (proc (bundleRef.get())) return true; - } - } - if (error != nullptr) - { - if (CFStringRef failureMessage = CFErrorCopyFailureReason (error)) - { - DBG (String::fromCFString (failureMessage)); - CFRelease (failureMessage); - } + if (error.object != nullptr) + if (auto failureMessage = CFUniquePtr (CFErrorCopyFailureReason (error.object))) + DBG (String::fromCFString (failureMessage.get())); - CFRelease (error); - } - - CFRelease (bundleRef); bundleRef = nullptr; } } diff --git a/modules/juce_audio_processors/format_types/juce_VSTPluginFormat.cpp b/modules/juce_audio_processors/format_types/juce_VSTPluginFormat.cpp index 647a6b55be..f3362872fc 100644 --- a/modules/juce_audio_processors/format_types/juce_VSTPluginFormat.cpp +++ b/modules/juce_audio_processors/format_types/juce_VSTPluginFormat.cpp @@ -711,7 +711,7 @@ struct ModuleHandle : public ReferenceCountedObject #endif #else Handle resHandle = {}; - CFBundleRef bundleRef = {}; + CFUniquePtr bundleRef; #if JUCE_MAC CFBundleRefNum resFileId = {}; @@ -729,26 +729,25 @@ struct ModuleHandle : public ReferenceCountedObject { auto* utf8 = file.getFullPathName().toRawUTF8(); - if (CFURLRef url = CFURLCreateFromFileSystemRepresentation (nullptr, (const UInt8*) utf8, - (CFIndex) strlen (utf8), file.isDirectory())) + if (auto url = CFUniquePtr (CFURLCreateFromFileSystemRepresentation (nullptr, (const UInt8*) utf8, + (CFIndex) strlen (utf8), file.isDirectory()))) { - bundleRef = CFBundleCreate (kCFAllocatorDefault, url); - CFRelease (url); + bundleRef.reset (CFBundleCreate (kCFAllocatorDefault, url.get())); if (bundleRef != nullptr) { - if (CFBundleLoadExecutable (bundleRef)) + if (CFBundleLoadExecutable (bundleRef.get())) { - moduleMain = (MainCall) CFBundleGetFunctionPointerForName (bundleRef, CFSTR("main_macho")); + moduleMain = (MainCall) CFBundleGetFunctionPointerForName (bundleRef.get(), CFSTR("main_macho")); if (moduleMain == nullptr) - moduleMain = (MainCall) CFBundleGetFunctionPointerForName (bundleRef, CFSTR("VSTPluginMain")); + moduleMain = (MainCall) CFBundleGetFunctionPointerForName (bundleRef.get(), CFSTR("VSTPluginMain")); JUCE_VST_WRAPPER_LOAD_CUSTOM_MAIN if (moduleMain != nullptr) { - if (CFTypeRef name = CFBundleGetValueForInfoDictionaryKey (bundleRef, CFSTR("CFBundleName"))) + if (CFTypeRef name = CFBundleGetValueForInfoDictionaryKey (bundleRef.get(), CFSTR("CFBundleName"))) { if (CFGetTypeID (name) == CFStringGetTypeID()) { @@ -763,7 +762,7 @@ struct ModuleHandle : public ReferenceCountedObject pluginName = file.getFileNameWithoutExtension(); #if JUCE_MAC - resFileId = CFBundleOpenBundleResourceMap (bundleRef); + resFileId = CFBundleOpenBundleResourceMap (bundleRef.get()); #endif ok = true; @@ -782,8 +781,7 @@ struct ModuleHandle : public ReferenceCountedObject if (! ok) { - CFBundleUnloadExecutable (bundleRef); - CFRelease (bundleRef); + CFBundleUnloadExecutable (bundleRef.get()); bundleRef = nullptr; } } @@ -798,14 +796,14 @@ struct ModuleHandle : public ReferenceCountedObject if (bundleRef != nullptr) { #if JUCE_MAC - CFBundleCloseBundleResourceMap (bundleRef, resFileId); + CFBundleCloseBundleResourceMap (bundleRef.get(), resFileId); #endif - if (CFGetRetainCount (bundleRef) == 1) - CFBundleUnloadExecutable (bundleRef); + if (CFGetRetainCount (bundleRef.get()) == 1) + CFBundleUnloadExecutable (bundleRef.get()); - if (CFGetRetainCount (bundleRef) > 0) - CFRelease (bundleRef); + if (CFGetRetainCount (bundleRef.get()) > 0) + bundleRef = nullptr; } } @@ -3633,16 +3631,11 @@ FileSearchPath VSTPluginFormat::getDefaultLocationsToSearch() return paths; #elif JUCE_IOS // on iOS you can only load plug-ins inside the hosts bundle folder - CFURLRef relativePluginDir = CFBundleCopyBuiltInPlugInsURL (CFBundleGetMainBundle()); - CFURLRef pluginDir = CFURLCopyAbsoluteURL (relativePluginDir); - CFRelease (relativePluginDir); - - CFStringRef path = CFURLCopyFileSystemPath (pluginDir, kCFURLPOSIXPathStyle); - CFRelease (pluginDir); - - FileSearchPath retval (String (CFStringGetCStringPtr (path, kCFStringEncodingUTF8))); - CFRelease (path); + CFUniquePtr relativePluginDir (CFBundleCopyBuiltInPlugInsURL (CFBundleGetMainBundle())); + CFUniquePtr pluginDir (CFURLCopyAbsoluteURL (relativePluginDir.get())); + CFStringRef path = CFURLCopyFileSystemPath (pluginDir.get(), kCFURLPOSIXPathStyle); + FileSearchPath retval (String (CFStringGetCStringPtr (path.get(), kCFStringEncodingUTF8))); return retval; #endif } diff --git a/modules/juce_core/native/juce_mac_SystemStats.mm b/modules/juce_core/native/juce_mac_SystemStats.mm index 4bbf8bee25..6d999ba3bc 100644 --- a/modules/juce_core/native/juce_mac_SystemStats.mm +++ b/modules/juce_core/native/juce_mac_SystemStats.mm @@ -292,9 +292,8 @@ String SystemStats::getComputerName() static String getLocaleValue (CFStringRef key) { - CFLocaleRef cfLocale = CFLocaleCopyCurrent(); - const String result (String::fromCFString ((CFStringRef) CFLocaleGetValue (cfLocale, key))); - CFRelease (cfLocale); + CFUniquePtr cfLocale (CFLocaleCopyCurrent()); + const String result (String::fromCFString ((CFStringRef) CFLocaleGetValue (cfLocale.get(), key))); return result; } @@ -303,9 +302,8 @@ String SystemStats::getUserRegion() { return getLocaleValue (kCFLocaleCountr String SystemStats::getDisplayLanguage() { - CFArrayRef cfPrefLangs = CFLocaleCopyPreferredLanguages(); - const String result (String::fromCFString ((CFStringRef) CFArrayGetValueAtIndex (cfPrefLangs, 0))); - CFRelease (cfPrefLangs); + CFUniquePtr cfPrefLangs (CFLocaleCopyPreferredLanguages()); + const String result (String::fromCFString ((CFStringRef) CFArrayGetValueAtIndex (cfPrefLangs.get(), 0))); return result; } diff --git a/modules/juce_core/native/juce_osx_ObjCHelpers.h b/modules/juce_core/native/juce_osx_ObjCHelpers.h index a9a7c8eb7c..ac1386bbc6 100644 --- a/modules/juce_core/native/juce_osx_ObjCHelpers.h +++ b/modules/juce_core/native/juce_osx_ObjCHelpers.h @@ -230,12 +230,50 @@ static ReturnType ObjCMsgSendSuper (id self, SEL sel, Params... params) //============================================================================== struct NSObjectDeleter { - void operator()(NSObject* object) const + void operator() (NSObject* object) const noexcept { - [object release]; + if (object != nullptr) + [object release]; } }; +template +using NSUniquePtr = std::unique_ptr; + +template +struct CFObjectDeleter +{ + void operator() (CFType object) const noexcept + { + if (object != nullptr) + CFRelease (object); + } +}; + +template +using CFUniquePtr = std::unique_ptr::type, CFObjectDeleter>; + +template +struct CFObjectHolder +{ + CFObjectHolder() = default; + + CFObjectHolder (const CFObjectHolder&) = delete; + CFObjectHolder (CFObjectHolder&&) = delete; + + CFObjectHolder& operator= (const CFObjectHolder&) = delete; + CFObjectHolder& operator= (CFObjectHolder&&) = delete; + + ~CFObjectHolder() noexcept + { + if (object != nullptr) + CFRelease (object); + } + + // Public to facilitate passing the pointer address to functions + CFType object = nullptr; +}; + //============================================================================== template struct ObjCClass @@ -417,19 +455,4 @@ private: BlockType block; }; -struct ScopedCFString -{ - ScopedCFString() = default; - ScopedCFString (String s) : cfString (s.toCFString()) {} - - ~ScopedCFString() noexcept - { - if (cfString != nullptr) - CFRelease (cfString); - } - - CFStringRef cfString = {}; -}; - - } // namespace juce diff --git a/modules/juce_events/native/juce_osx_MessageQueue.h b/modules/juce_events/native/juce_osx_MessageQueue.h index 2d2ac36727..b32cb0ece5 100644 --- a/modules/juce_events/native/juce_osx_MessageQueue.h +++ b/modules/juce_events/native/juce_osx_MessageQueue.h @@ -40,15 +40,14 @@ public: zerostruct (sourceContext); // (can't use "= { 0 }" on this object because it's typedef'ed as a C struct) sourceContext.info = this; sourceContext.perform = runLoopSourceCallback; - runLoopSource = CFRunLoopSourceCreate (kCFAllocatorDefault, 1, &sourceContext); - CFRunLoopAddSource (runLoop, runLoopSource, kCFRunLoopCommonModes); + runLoopSource.reset (CFRunLoopSourceCreate (kCFAllocatorDefault, 1, &sourceContext)); + CFRunLoopAddSource (runLoop, runLoopSource.get(), kCFRunLoopCommonModes); } ~MessageQueue() noexcept { - CFRunLoopRemoveSource (runLoop, runLoopSource, kCFRunLoopCommonModes); - CFRunLoopSourceInvalidate (runLoopSource); - CFRelease (runLoopSource); + CFRunLoopRemoveSource (runLoop, runLoopSource.get(), kCFRunLoopCommonModes); + CFRunLoopSourceInvalidate (runLoopSource.get()); } void post (MessageManager::MessageBase* const message) @@ -60,11 +59,11 @@ public: private: ReferenceCountedArray messages; CFRunLoopRef runLoop; - CFRunLoopSourceRef runLoopSource; + CFUniquePtr runLoopSource; void wakeUp() noexcept { - CFRunLoopSourceSignal (runLoopSource); + CFRunLoopSourceSignal (runLoopSource.get()); CFRunLoopWakeUp (runLoop); } diff --git a/modules/juce_graphics/native/juce_mac_CoreGraphicsContext.mm b/modules/juce_graphics/native/juce_mac_CoreGraphicsContext.mm index de6ffecfcd..4cc4439026 100644 --- a/modules/juce_graphics/native/juce_mac_CoreGraphicsContext.mm +++ b/modules/juce_graphics/native/juce_mac_CoreGraphicsContext.mm @@ -118,9 +118,10 @@ public: if (mustOutliveSource) { - CFDataRef data = CFDataCreate (nullptr, (const UInt8*) srcData.data, (CFIndex) ((size_t) srcData.lineStride * (size_t) srcData.height)); - provider = detail::DataProviderPtr { CGDataProviderCreateWithCFData (data) }; - CFRelease (data); + CFUniquePtr data (CFDataCreate (nullptr, + (const UInt8*) srcData.data, + (CFIndex) ((size_t) srcData.lineStride * (size_t) srcData.height))); + provider = detail::DataProviderPtr { CGDataProviderCreateWithCFData (data.get()) }; } else { @@ -845,12 +846,11 @@ Image juce_loadWithCoreImage (InputStream& input) memBlockHolder->block.getData(), memBlockHolder->block.getSize(), [] (void * __nullable info, const void*, size_t) { delete (MemoryBlockHolder::Ptr*) info; }) }; - auto imageSource = CGImageSourceCreateWithDataProvider (provider.get(), nullptr); - if (imageSource != nullptr) + if (auto imageSource = CFUniquePtr (CGImageSourceCreateWithDataProvider (provider.get(), nullptr))) { - auto loadedImage = CGImageSourceCreateImageAtIndex (imageSource, 0, nullptr); - CFRelease (imageSource); + CFUniquePtr loadedImagePtr (CGImageSourceCreateImageAtIndex (imageSource.get(), 0, nullptr)); + auto* loadedImage = loadedImagePtr.get(); #endif if (loadedImage != nullptr) @@ -871,10 +871,6 @@ Image juce_loadWithCoreImage (InputStream& input) CGContextDrawImage (cgImage->context.get(), convertToCGRect (image.getBounds()), loadedImage); CGContextFlush (cgImage->context.get()); - #if ! JUCE_IOS - CFRelease (loadedImage); - #endif - // Because it's impossible to create a truly 24-bit CG image, this flag allows a user // to find out whether the file they just loaded the image from had an alpha channel or not. image.getProperties()->set ("originalImageHadAlpha", hasAlphaChan); diff --git a/modules/juce_graphics/native/juce_mac_Fonts.mm b/modules/juce_graphics/native/juce_mac_Fonts.mm index ff0a23a9f9..cafe3e4546 100644 --- a/modules/juce_graphics/native/juce_mac_Fonts.mm +++ b/modules/juce_graphics/native/juce_mac_Fonts.mm @@ -59,35 +59,28 @@ namespace CoreTextTypeLayout return referenceFontSize / getFontTotalHeight (font); } - static CTFontRef getFontWithPointSize (CTFontRef font, float size) + static CFUniquePtr getFontWithPointSize (CTFontRef font, float pointSize) { - auto newFont = CTFontCreateCopyWithAttributes (font, size, nullptr, nullptr); - CFRelease (font); - return newFont; + return CFUniquePtr (CTFontCreateCopyWithAttributes (font, pointSize, nullptr, nullptr)); } - static CTFontRef createCTFont (const Font& font, const float fontSizePoints, CGAffineTransform& transformRequired) + static CFUniquePtr createCTFont (const Font& font, const float fontSizePoints, CGAffineTransform& transformRequired) { - auto cfFontFamily = FontStyleHelpers::getConcreteFamilyName (font).toCFString(); - auto cfFontStyle = findBestAvailableStyle (font, transformRequired).toCFString(); + CFUniquePtr cfFontFamily (FontStyleHelpers::getConcreteFamilyName (font).toCFString()); + CFUniquePtr cfFontStyle (findBestAvailableStyle (font, transformRequired).toCFString()); CFStringRef keys[] = { kCTFontFamilyNameAttribute, kCTFontStyleNameAttribute }; - CFTypeRef values[] = { cfFontFamily, cfFontStyle }; + CFTypeRef values[] = { cfFontFamily.get(), cfFontStyle.get() }; - auto fontDescAttributes = CFDictionaryCreate (nullptr, (const void**) &keys, - (const void**) &values, - numElementsInArray (keys), - &kCFTypeDictionaryKeyCallBacks, - &kCFTypeDictionaryValueCallBacks); - CFRelease (cfFontStyle); + CFUniquePtr fontDescAttributes (CFDictionaryCreate (nullptr, + (const void**) &keys, + (const void**) &values, + numElementsInArray (keys), + &kCFTypeDictionaryKeyCallBacks, + &kCFTypeDictionaryValueCallBacks)); - auto ctFontDescRef = CTFontDescriptorCreateWithAttributes (fontDescAttributes); - CFRelease (fontDescAttributes); + CFUniquePtr ctFontDescRef (CTFontDescriptorCreateWithAttributes (fontDescAttributes.get())); - auto ctFontRef = CTFontCreateWithFontDescriptor (ctFontDescRef, fontSizePoints, nullptr); - CFRelease (ctFontDescRef); - CFRelease (cfFontFamily); - - return ctFontRef; + return CFUniquePtr (CTFontCreateWithFontDescriptor (ctFontDescRef.get(), fontSizePoints, nullptr)); } //============================================================================== @@ -151,12 +144,12 @@ namespace CoreTextTypeLayout CGFloat ascent, descent, leading; }; - static CTFontRef getOrCreateFont (const Font& f) + static CFUniquePtr getOrCreateFont (const Font& f) { if (auto ctf = getCTFontFromTypeface (f)) { CFRetain (ctf); - return ctf; + return CFUniquePtr (ctf); } CGAffineTransform transform; @@ -205,14 +198,13 @@ namespace CoreTextTypeLayout } //============================================================================== - static CFAttributedStringRef createCFAttributedString (const AttributedString& text) + static CFUniquePtr createCFAttributedString (const AttributedString& text) { const detail::ColorSpacePtr rgbColourSpace { CGColorSpaceCreateWithName (kCGColorSpaceSRGB) }; auto attribString = CFAttributedStringCreateMutable (kCFAllocatorDefault, 0); - auto cfText = text.getText().toCFString(); - CFAttributedStringReplaceString (attribString, CFRangeMake (0, 0), cfText); - CFRelease (cfText); + CFUniquePtr cfText (text.getText().toCFString()); + CFAttributedStringReplaceString (attribString, CFRangeMake (0, 0), cfText.get()); auto numCharacterAttributes = text.getNumAttributes(); auto attribStringLen = CFAttributedStringGetLength (attribString); @@ -229,16 +221,15 @@ namespace CoreTextTypeLayout if (auto ctFontRef = getOrCreateFont (attr.font)) { - ctFontRef = getFontWithPointSize (ctFontRef, attr.font.getHeight() * getHeightToPointsFactor (ctFontRef)); - CFAttributedStringSetAttribute (attribString, range, kCTFontAttributeName, ctFontRef); + ctFontRef = getFontWithPointSize (ctFontRef.get(), attr.font.getHeight() * getHeightToPointsFactor (ctFontRef.get())); + CFAttributedStringSetAttribute (attribString, range, kCTFontAttributeName, ctFontRef.get()); if (attr.font.isUnderlined()) { auto underline = kCTUnderlineStyleSingle; - auto numberRef = CFNumberCreate (nullptr, kCFNumberIntType, &underline); - CFAttributedStringSetAttribute (attribString, range, kCTUnderlineStyleAttributeName, numberRef); - CFRelease (numberRef); + CFUniquePtr numberRef (CFNumberCreate (nullptr, kCFNumberIntType, &underline)); + CFAttributedStringSetAttribute (attribString, range, kCTUnderlineStyleAttributeName, numberRef.get()); } auto extraKerning = attr.font.getExtraKerningFactor(); @@ -247,12 +238,9 @@ namespace CoreTextTypeLayout { extraKerning *= attr.font.getHeight(); - auto numberRef = CFNumberCreate (nullptr, kCFNumberFloatType, &extraKerning); - CFAttributedStringSetAttribute (attribString, range, kCTKernAttributeName, numberRef); - CFRelease (numberRef); + CFUniquePtr numberRef (CFNumberCreate (nullptr, kCFNumberFloatType, &extraKerning)); + CFAttributedStringSetAttribute (attribString, range, kCTKernAttributeName, numberRef.get()); } - - CFRelease (ctFontRef); } { @@ -283,40 +271,33 @@ namespace CoreTextTypeLayout { kCTParagraphStyleSpecifierLineSpacingAdjustment, sizeof (CGFloat), &ctLineSpacing } }; - auto ctParagraphStyleRef = CTParagraphStyleCreate (settings, (size_t) numElementsInArray (settings)); + CFUniquePtr ctParagraphStyleRef (CTParagraphStyleCreate (settings, (size_t) numElementsInArray (settings))); CFAttributedStringSetAttribute (attribString, CFRangeMake (0, CFAttributedStringGetLength (attribString)), - kCTParagraphStyleAttributeName, ctParagraphStyleRef); - CFRelease (ctParagraphStyleRef); - return attribString; + kCTParagraphStyleAttributeName, ctParagraphStyleRef.get()); + return CFUniquePtr (attribString); } - static CTFramesetterRef createCTFramesetter (const AttributedString& text) + static CFUniquePtr createCTFramesetter (const AttributedString& text) { auto attribString = createCFAttributedString (text); - auto framesetter = CTFramesetterCreateWithAttributedString (attribString); - CFRelease (attribString); - - return framesetter; + return CFUniquePtr (CTFramesetterCreateWithAttributedString (attribString.get())); } - static CTFrameRef createCTFrame (CTFramesetterRef framesetter, CGRect bounds) + static CFUniquePtr createCTFrame (CTFramesetterRef framesetter, CGRect bounds) { auto path = CGPathCreateMutable(); CGPathAddRect (path, nullptr, bounds); - auto frame = CTFramesetterCreateFrame (framesetter, CFRangeMake (0, 0), path, nullptr); + CFUniquePtr frame (CTFramesetterCreateFrame (framesetter, CFRangeMake (0, 0), path, nullptr)); CGPathRelease (path); return frame; } - static CTFrameRef createCTFrame (const AttributedString& text, CGRect bounds) + static CFUniquePtr createCTFrame (const AttributedString& text, CGRect bounds) { auto framesetter = createCTFramesetter (text); - auto frame = createCTFrame (framesetter, bounds); - CFRelease (framesetter); - - return frame; + return createCTFrame (framesetter.get(), bounds); } static Range getLineVerticalRange (CTFrameRef frame, CFArrayRef lines, int lineIndex) @@ -353,7 +334,7 @@ namespace CoreTextTypeLayout CFRange fitrange; auto suggestedSingleLineFrameSize = - CTFramesetterSuggestFrameSizeWithConstraints (framesetter, CFRangeMake (0, 0), nullptr, + CTFramesetterSuggestFrameSizeWithConstraints (framesetter.get(), CFRangeMake (0, 0), nullptr, CGSizeMake (CGFLOAT_MAX, CGFLOAT_MAX), &fitrange); auto minCTFrameHeight = (float) suggestedSingleLineFrameSize.height; @@ -375,9 +356,8 @@ namespace CoreTextTypeLayout return frameArea; }(); - auto frame = createCTFrame (framesetter, CGRectMake ((CGFloat) ctFrameArea.getX(), flipHeight - (CGFloat) ctFrameArea.getBottom(), - (CGFloat) ctFrameArea.getWidth(), (CGFloat) ctFrameArea.getHeight())); - CFRelease (framesetter); + auto frame = createCTFrame (framesetter.get(), CGRectMake ((CGFloat) ctFrameArea.getX(), flipHeight - (CGFloat) ctFrameArea.getBottom(), + (CGFloat) ctFrameArea.getWidth(), (CGFloat) ctFrameArea.getHeight())); auto textMatrix = CGContextGetTextMatrix (context); CGContextSaveGState (context); @@ -385,7 +365,7 @@ namespace CoreTextTypeLayout if (verticalJustification == Justification::verticallyCentred || verticalJustification == Justification::bottom) { - auto adjust = ctFrameArea.getHeight() - findCTFrameHeight (frame); + auto adjust = ctFrameArea.getHeight() - findCTFrameHeight (frame.get()); if (verticalJustification == Justification::verticallyCentred) adjust *= 0.5f; @@ -393,19 +373,17 @@ namespace CoreTextTypeLayout CGContextTranslateCTM (context, 0, -adjust); } - CTFrameDraw (frame, context); + CTFrameDraw (frame.get(), context); CGContextRestoreGState (context); CGContextSetTextMatrix (context, textMatrix); - - CFRelease (frame); } static void createLayout (TextLayout& glyphLayout, const AttributedString& text) { auto boundsHeight = glyphLayout.getHeight(); auto frame = createCTFrame (text, CGRectMake (0, 0, glyphLayout.getWidth(), boundsHeight)); - auto lines = CTFrameGetLines (frame); + auto lines = CTFrameGetLines (frame.get()); auto numLines = CFArrayGetCount (lines); glyphLayout.ensureStorageAllocated ((int) numLines); @@ -420,7 +398,7 @@ namespace CoreTextTypeLayout auto lineStringEnd = cfrlineStringRange.location + cfrlineStringRange.length; Range lineStringRange ((int) cfrlineStringRange.location, (int) lineStringEnd); - LineInfo lineInfo (frame, line, i); + LineInfo lineInfo (frame.get(), line, i); auto glyphLine = std::make_unique (lineStringRange, Point ((float) lineInfo.origin.x, @@ -446,18 +424,16 @@ namespace CoreTextTypeLayout CTFontRef ctRunFont; if (CFDictionaryGetValueIfPresent (runAttributes, kCTFontAttributeName, (const void**) &ctRunFont)) { - auto cfsFontName = CTFontCopyPostScriptName (ctRunFont); - auto ctFontRef = CTFontCreateWithName (cfsFontName, referenceFontSize, nullptr); - CFRelease (cfsFontName); + CFUniquePtr cfsFontName (CTFontCopyPostScriptName (ctRunFont)); + CFUniquePtr ctFontRef (CTFontCreateWithName (cfsFontName.get(), referenceFontSize, nullptr)); - auto fontHeightToPointsFactor = getHeightToPointsFactor (ctFontRef); - CFRelease (ctFontRef); + auto fontHeightToPointsFactor = getHeightToPointsFactor (ctFontRef.get()); - auto cfsFontFamily = (CFStringRef) CTFontCopyAttribute (ctRunFont, kCTFontFamilyNameAttribute); - auto cfsFontStyle = (CFStringRef) CTFontCopyAttribute (ctRunFont, kCTFontStyleNameAttribute); + CFUniquePtr cfsFontFamily ((CFStringRef) CTFontCopyAttribute (ctRunFont, kCTFontFamilyNameAttribute)); + CFUniquePtr cfsFontStyle ((CFStringRef) CTFontCopyAttribute (ctRunFont, kCTFontStyleNameAttribute)); - glyphRun->font = Font (String::fromCFString (cfsFontFamily), - String::fromCFString (cfsFontStyle), + glyphRun->font = Font (String::fromCFString (cfsFontFamily.get()), + String::fromCFString (cfsFontStyle.get()), (float) (CTFontGetSize (ctRunFont) / fontHeightToPointsFactor)); auto isUnderlined = [&] @@ -479,9 +455,6 @@ namespace CoreTextTypeLayout }(); glyphRun->font.setUnderline (isUnderlined); - - CFRelease (cfsFontStyle); - CFRelease (cfsFontFamily); } CGColorRef cgRunColor; @@ -509,8 +482,6 @@ namespace CoreTextTypeLayout glyphLayout.addLine (std::move (glyphLine)); } - - CFRelease (frame); } } @@ -526,7 +497,7 @@ public: if (ctFontRef != nullptr) { - fontRef = CTFontCopyGraphicsFont (ctFontRef, nullptr); + fontRef = CTFontCopyGraphicsFont (ctFontRef.get(), nullptr); initialiseMetrics(); } } @@ -536,10 +507,9 @@ public: { // We can't use CFDataCreate here as this triggers a false positive in ASAN // so copy the data manually and use CFDataCreateWithBytesNoCopy - auto cfData = CFDataCreateWithBytesNoCopy (kCFAllocatorDefault, (const UInt8*) dataCopy.getData(), - (CFIndex) dataCopy.getSize(), kCFAllocatorNull); - auto provider = CGDataProviderCreateWithCFData (cfData); - CFRelease (cfData); + CFUniquePtr cfData (CFDataCreateWithBytesNoCopy (kCFAllocatorDefault, (const UInt8*) dataCopy.getData(), + (CFIndex) dataCopy.getSize(), kCFAllocatorNull)); + auto provider = CGDataProviderCreateWithCFData (cfData.get()); #if JUCE_IOS // Workaround for a an obscure iOS bug which can cause the app to dead-lock @@ -558,21 +528,15 @@ public: canBeUsedForLayout = CTFontManagerRegisterGraphicsFont (fontRef, nullptr); #endif - ctFontRef = CTFontCreateWithGraphicsFont (fontRef, referenceFontSize, nullptr, nullptr); + ctFontRef.reset (CTFontCreateWithGraphicsFont (fontRef, referenceFontSize, nullptr, nullptr)); if (ctFontRef != nullptr) { - if (auto fontName = CTFontCopyName (ctFontRef, kCTFontFamilyNameKey)) - { - name = String::fromCFString (fontName); - CFRelease (fontName); - } + if (auto fontName = CFUniquePtr (CTFontCopyName (ctFontRef.get(), kCTFontFamilyNameKey))) + name = String::fromCFString (fontName.get()); - if (auto fontStyle = CTFontCopyName (ctFontRef, kCTFontStyleNameKey)) - { - style = String::fromCFString (fontStyle); - CFRelease (fontStyle); - } + if (auto fontStyle = CFUniquePtr (CTFontCopyName (ctFontRef.get(), kCTFontStyleNameKey))) + style = String::fromCFString (fontStyle.get()); initialiseMetrics(); } @@ -581,8 +545,8 @@ public: void initialiseMetrics() { - auto ctAscent = std::abs ((float) CTFontGetAscent (ctFontRef)); - auto ctDescent = std::abs ((float) CTFontGetDescent (ctFontRef)); + auto ctAscent = std::abs ((float) CTFontGetAscent (ctFontRef.get())); + auto ctDescent = std::abs ((float) CTFontGetDescent (ctFontRef.get())); auto ctTotalHeight = ctAscent + ctDescent; ascent = ctAscent / ctTotalHeight; @@ -592,21 +556,17 @@ public: fontHeightToPointsFactor = referenceFontSize / ctTotalHeight; const short zero = 0; - auto numberRef = CFNumberCreate (nullptr, kCFNumberShortType, &zero); + CFUniquePtr numberRef (CFNumberCreate (nullptr, kCFNumberShortType, &zero)); CFStringRef keys[] = { kCTFontAttributeName, kCTLigatureAttributeName }; - CFTypeRef values[] = { ctFontRef, numberRef }; - attributedStringAtts = CFDictionaryCreate (nullptr, (const void**) &keys, - (const void**) &values, numElementsInArray (keys), - &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks); - CFRelease (numberRef); + CFTypeRef values[] = { ctFontRef.get(), numberRef.get() }; + attributedStringAtts.reset (CFDictionaryCreate (nullptr, (const void**) &keys, + (const void**) &values, numElementsInArray (keys), + &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks)); } ~OSXTypeface() override { - if (attributedStringAtts != nullptr) - CFRelease (attributedStringAtts); - if (fontRef != nullptr) { #if JUCE_MAC && defined (MAC_OS_X_VERSION_10_8) && MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_8 @@ -616,9 +576,6 @@ public: CGFontRelease (fontRef); } - - if (ctFontRef != nullptr) - CFRelease (ctFontRef); } float getAscent() const override { return ascent; } @@ -631,12 +588,11 @@ public: if (ctFontRef != nullptr && text.isNotEmpty()) { - auto cfText = text.toCFString(); - auto attribString = CFAttributedStringCreate (kCFAllocatorDefault, cfText, attributedStringAtts); - CFRelease (cfText); + CFUniquePtr cfText (text.toCFString()); + CFUniquePtr attribString (CFAttributedStringCreate (kCFAllocatorDefault, cfText.get(), attributedStringAtts.get())); - auto line = CTLineCreateWithAttributedString (attribString); - auto runArray = CTLineGetGlyphRuns (line); + CFUniquePtr line (CTLineCreateWithAttributedString (attribString.get())); + auto runArray = CTLineGetGlyphRuns (line.get()); for (CFIndex i = 0; i < CFArrayGetCount (runArray); ++i) { @@ -649,9 +605,6 @@ public: x += (float) advances.advances[j].width; } - CFRelease (line); - CFRelease (attribString); - x *= unitsToHeightScaleFactor; } @@ -666,12 +619,11 @@ public: { float x = 0; - auto cfText = text.toCFString(); - auto attribString = CFAttributedStringCreate (kCFAllocatorDefault, cfText, attributedStringAtts); - CFRelease (cfText); + CFUniquePtr cfText (text.toCFString()); + CFUniquePtr attribString (CFAttributedStringCreate (kCFAllocatorDefault, cfText.get(), attributedStringAtts.get())); - auto line = CTLineCreateWithAttributedString (attribString); - auto runArray = CTLineGetGlyphRuns (line); + CFUniquePtr line (CTLineCreateWithAttributedString (attribString.get())); + auto runArray = CTLineGetGlyphRuns (line.get()); for (CFIndex i = 0; i < CFArrayGetCount (runArray); ++i) { @@ -688,9 +640,6 @@ public: resultGlyphs.add (glyphs.glyphs[j]); } } - - CFRelease (line); - CFRelease (attribString); } } @@ -698,10 +647,9 @@ public: { jassert (path.isEmpty()); // we might need to apply a transform to the path, so this must be empty - if (auto pathRef = CTFontCreatePathForGlyph (ctFontRef, (CGGlyph) glyphNumber, &renderingTransform)) + if (auto pathRef = CFUniquePtr (CTFontCreatePathForGlyph (ctFontRef.get(), (CGGlyph) glyphNumber, &renderingTransform))) { - CGPathApply (pathRef, &path, pathApplier); - CFRelease (pathRef); + CGPathApply (pathRef.get(), &path, pathApplier); if (! pathTransform.isIdentity()) path.applyTransform (pathTransform); @@ -714,7 +662,7 @@ public: //============================================================================== CGFontRef fontRef = {}; - CTFontRef ctFontRef = {}; + CFUniquePtr ctFontRef; float fontHeightToPointsFactor = 1.0f; CGAffineTransform renderingTransform = CGAffineTransformIdentity; @@ -723,7 +671,7 @@ public: private: MemoryBlock dataCopy; - CFDictionaryRef attributedStringAtts = {}; + CFUniquePtr attributedStringAtts; float ascent = 0, unitsToHeightScaleFactor = 0; AffineTransform pathTransform; @@ -752,7 +700,7 @@ private: CTFontRef getCTFontFromTypeface (const Font& f) { if (auto* tf = dynamic_cast (f.getTypeface())) - return tf->ctFontRef; + return tf->ctFontRef.get(); return {}; } @@ -763,33 +711,26 @@ StringArray Font::findAllTypefaceNames() #if JUCE_MAC // CTFontManager only exists on OS X 10.6 and later, it does not exist on iOS - auto fontFamilyArray = CTFontManagerCopyAvailableFontFamilyNames(); + CFUniquePtr fontFamilyArray (CTFontManagerCopyAvailableFontFamilyNames()); - for (CFIndex i = 0; i < CFArrayGetCount (fontFamilyArray); ++i) + for (CFIndex i = 0; i < CFArrayGetCount (fontFamilyArray.get()); ++i) { - auto family = String::fromCFString ((CFStringRef) CFArrayGetValueAtIndex (fontFamilyArray, i)); + auto family = String::fromCFString ((CFStringRef) CFArrayGetValueAtIndex (fontFamilyArray.get(), i)); if (! family.startsWithChar ('.')) // ignore fonts that start with a '.' names.addIfNotAlreadyThere (family); } - - CFRelease (fontFamilyArray); #else - auto fontCollectionRef = CTFontCollectionCreateFromAvailableFonts (nullptr); - auto fontDescriptorArray = CTFontCollectionCreateMatchingFontDescriptors (fontCollectionRef); - CFRelease (fontCollectionRef); + CFUniquePtr fontCollectionRef (CTFontCollectionCreateFromAvailableFonts (nullptr)); + CFUniquePtr fontDescriptorArray (CTFontCollectionCreateMatchingFontDescriptors (fontCollectionRef.get())); - for (CFIndex i = 0; i < CFArrayGetCount (fontDescriptorArray); ++i) + for (CFIndex i = 0; i < CFArrayGetCount (fontDescriptorArray.get()); ++i) { - auto ctFontDescriptorRef = (CTFontDescriptorRef) CFArrayGetValueAtIndex (fontDescriptorArray, i); - auto cfsFontFamily = (CFStringRef) CTFontDescriptorCopyAttribute (ctFontDescriptorRef, kCTFontFamilyNameAttribute); + auto ctFontDescriptorRef = (CTFontDescriptorRef) CFArrayGetValueAtIndex (fontDescriptorArray.get(), i); + CFUniquePtr cfsFontFamily ((CFStringRef) CTFontDescriptorCopyAttribute (ctFontDescriptorRef, kCTFontFamilyNameAttribute)); - names.addIfNotAlreadyThere (String::fromCFString (cfsFontFamily)); - - CFRelease (cfsFontFamily); + names.addIfNotAlreadyThere (String::fromCFString (cfsFontFamily.get())); } - - CFRelease (fontDescriptorArray); #endif names.sort (true); @@ -803,37 +744,26 @@ StringArray Font::findAllTypefaceStyles (const String& family) StringArray results; - auto cfsFontFamily = family.toCFString(); + CFUniquePtr cfsFontFamily (family.toCFString()); CFStringRef keys[] = { kCTFontFamilyNameAttribute }; - CFTypeRef values[] = { cfsFontFamily }; + CFTypeRef values[] = { cfsFontFamily.get() }; - auto fontDescAttributes = CFDictionaryCreate (nullptr, (const void**) &keys, (const void**) &values, numElementsInArray (keys), - &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks); - CFRelease (cfsFontFamily); + CFUniquePtr fontDescAttributes (CFDictionaryCreate (nullptr, (const void**) &keys, (const void**) &values, numElementsInArray (keys), + &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks)); - auto ctFontDescRef = CTFontDescriptorCreateWithAttributes (fontDescAttributes); - CFRelease (fontDescAttributes); + CFUniquePtr ctFontDescRef (CTFontDescriptorCreateWithAttributes (fontDescAttributes.get())); + CFUniquePtr fontFamilyArray (CFArrayCreate (kCFAllocatorDefault, (const void**) &ctFontDescRef, 1, &kCFTypeArrayCallBacks)); - auto fontFamilyArray = CFArrayCreate (kCFAllocatorDefault, (const void**) &ctFontDescRef, 1, &kCFTypeArrayCallBacks); - CFRelease (ctFontDescRef); + CFUniquePtr fontCollectionRef (CTFontCollectionCreateWithFontDescriptors (fontFamilyArray.get(), nullptr)); - auto fontCollectionRef = CTFontCollectionCreateWithFontDescriptors (fontFamilyArray, nullptr); - CFRelease (fontFamilyArray); - - auto fontDescriptorArray = CTFontCollectionCreateMatchingFontDescriptors (fontCollectionRef); - CFRelease (fontCollectionRef); - - if (fontDescriptorArray != nullptr) + if (auto fontDescriptorArray = CFUniquePtr (CTFontCollectionCreateMatchingFontDescriptors (fontCollectionRef.get()))) { - for (CFIndex i = 0; i < CFArrayGetCount (fontDescriptorArray); ++i) + for (CFIndex i = 0; i < CFArrayGetCount (fontDescriptorArray.get()); ++i) { - auto ctFontDescriptorRef = (CTFontDescriptorRef) CFArrayGetValueAtIndex (fontDescriptorArray, i); - auto cfsFontStyle = (CFStringRef) CTFontDescriptorCopyAttribute (ctFontDescriptorRef, kCTFontStyleNameAttribute); - results.add (String::fromCFString (cfsFontStyle)); - CFRelease (cfsFontStyle); + auto ctFontDescriptorRef = (CTFontDescriptorRef) CFArrayGetValueAtIndex (fontDescriptorArray.get(), i); + CFUniquePtr cfsFontStyle ((CFStringRef) CTFontDescriptorCopyAttribute (ctFontDescriptorRef, kCTFontStyleNameAttribute)); + results.add (String::fromCFString (cfsFontStyle.get())); } - - CFRelease (fontDescriptorArray); } return results; @@ -847,13 +777,8 @@ Typeface::Ptr Typeface::createSystemTypefaceFor (const void* data, size_t size) void Typeface::scanFolderForFonts (const File& folder) { for (auto& file : folder.findChildFiles (File::findFiles, false, "*.otf;*.ttf")) - { - if (auto urlref = CFURLCreateWithFileSystemPath (kCFAllocatorDefault, file.getFullPathName().toCFString(), kCFURLPOSIXPathStyle, true)) - { - CTFontManagerRegisterFontsForURL (urlref, kCTFontManagerScopeProcess, nullptr); - CFRelease (urlref); - } - } + if (auto urlref = CFUniquePtr (CFURLCreateWithFileSystemPath (kCFAllocatorDefault, file.getFullPathName().toCFString(), kCFURLPOSIXPathStyle, true))) + CTFontManagerRegisterFontsForURL (urlref.get(), kCTFontManagerScopeProcess, nullptr); } struct DefaultFontNames diff --git a/modules/juce_graphics/native/juce_mac_IconHelpers.cpp b/modules/juce_graphics/native/juce_mac_IconHelpers.cpp index b90ebb4643..e1f7c765e4 100644 --- a/modules/juce_graphics/native/juce_mac_IconHelpers.cpp +++ b/modules/juce_graphics/native/juce_mac_IconHelpers.cpp @@ -108,44 +108,34 @@ static Image getIconFromIcnsFile (const File& icnsFile, const int size) Image JUCE_API getIconFromApplication (const String& applicationPath, const int size) { - Image hostIcon; - - if (CFStringRef pathCFString = CFStringCreateWithCString (kCFAllocatorDefault, applicationPath.toRawUTF8(), kCFStringEncodingUTF8)) + if (auto pathCFString = CFUniquePtr (CFStringCreateWithCString (kCFAllocatorDefault, applicationPath.toRawUTF8(), kCFStringEncodingUTF8))) { - if (CFURLRef url = CFURLCreateWithFileSystemPath (kCFAllocatorDefault, pathCFString, kCFURLPOSIXPathStyle, 1)) + if (auto url = CFUniquePtr (CFURLCreateWithFileSystemPath (kCFAllocatorDefault, pathCFString.get(), kCFURLPOSIXPathStyle, 1))) { - if (CFBundleRef appBundle = CFBundleCreate (kCFAllocatorDefault, url)) + if (auto appBundle = CFUniquePtr (CFBundleCreate (kCFAllocatorDefault, url.get()))) { - if (CFTypeRef infoValue = CFBundleGetValueForInfoDictionaryKey (appBundle, CFSTR("CFBundleIconFile"))) + if (CFTypeRef infoValue = CFBundleGetValueForInfoDictionaryKey (appBundle.get(), CFSTR("CFBundleIconFile"))) { if (CFGetTypeID (infoValue) == CFStringGetTypeID()) { CFStringRef iconFilename = reinterpret_cast (infoValue); CFStringRef resourceURLSuffix = CFStringHasSuffix (iconFilename, CFSTR(".icns")) ? nullptr : CFSTR("icns"); - if (CFURLRef iconURL = CFBundleCopyResourceURL (appBundle, iconFilename, resourceURLSuffix, nullptr)) - { - if (CFStringRef iconPath = CFURLCopyFileSystemPath (iconURL, kCFURLPOSIXPathStyle)) - { - File icnsFile (CFStringGetCStringPtr (iconPath, CFStringGetSystemEncoding())); - hostIcon = getIconFromIcnsFile (icnsFile, size); - CFRelease (iconPath); - } - CFRelease (iconURL); + if (auto iconURL = CFUniquePtr (CFBundleCopyResourceURL (appBundle.get(), iconFilename, resourceURLSuffix, nullptr))) + { + if (auto iconPath = CFUniquePtr (CFURLCopyFileSystemPath (iconURL.get(), kCFURLPOSIXPathStyle))) + { + File icnsFile (CFStringGetCStringPtr (iconPath.get(), CFStringGetSystemEncoding())); + return getIconFromIcnsFile (icnsFile, size); + } } } } - - CFRelease (appBundle); } - - CFRelease (url); } - - CFRelease (pathCFString); } - return hostIcon; + return {}; } } // namespace juce diff --git a/modules/juce_gui_basics/native/juce_ios_ContentSharer.cpp b/modules/juce_gui_basics/native/juce_ios_ContentSharer.cpp index 8aa6603c6e..4b5cce202a 100644 --- a/modules/juce_gui_basics/native/juce_ios_ContentSharer.cpp +++ b/modules/juce_gui_basics/native/juce_ios_ContentSharer.cpp @@ -191,8 +191,8 @@ private: ContentSharer& owner; UIViewComponentPeer* peer = nullptr; - std::unique_ptr controller; - std::unique_ptr, NSObjectDeleter> popoverDelegate; + NSUniquePtr controller; + NSUniquePtr> popoverDelegate; bool succeeded = false; String errorDescription; diff --git a/modules/juce_gui_basics/native/juce_ios_FileChooser.mm b/modules/juce_gui_basics/native/juce_ios_FileChooser.mm index d61b73f0be..3d8d00c3f6 100644 --- a/modules/juce_gui_basics/native/juce_ios_FileChooser.mm +++ b/modules/juce_gui_basics/native/juce_ios_FileChooser.mm @@ -189,20 +189,13 @@ private: jassert (filter.upToLastOccurrenceOf (".", true, false) == "*."); auto fileExtension = filter.fromLastOccurrenceOf (".", false, false); - auto fileExtensionCF = fileExtension.toCFString(); + CFUniquePtr fileExtensionCF (fileExtension.toCFString()); if (firstExtension.isEmpty()) firstExtension = fileExtension; - auto tag = UTTypeCreatePreferredIdentifierForTag (kUTTagClassFilenameExtension, fileExtensionCF, nullptr); - - if (tag != nullptr) - { - result.add (String::fromCFString (tag)); - CFRelease (tag); - } - - CFRelease (fileExtensionCF); + if (auto tag = CFUniquePtr (UTTypeCreatePreferredIdentifierForTag (kUTTagClassFilenameExtension, fileExtensionCF.get(), nullptr))) + result.add (String::fromCFString (tag.get())); } } else @@ -358,8 +351,8 @@ private: //============================================================================== FileChooser& owner; - std::unique_ptr, NSObjectDeleter> delegate; - std::unique_ptr controller; + NSUniquePtr> delegate; + NSUniquePtr controller; UIViewComponentPeer* peer = nullptr; static FileChooserDelegateClass fileChooserDelegateClass; diff --git a/modules/juce_gui_basics/native/juce_mac_NSViewComponentPeer.mm b/modules/juce_gui_basics/native/juce_mac_NSViewComponentPeer.mm index 2c0dcf5462..c929d51d48 100644 --- a/modules/juce_gui_basics/native/juce_mac_NSViewComponentPeer.mm +++ b/modules/juce_gui_basics/native/juce_mac_NSViewComponentPeer.mm @@ -808,7 +808,7 @@ public: { // (need to retain this in case a modal loop runs in handleKeyEvent and // our event object gets lost) - const std::unique_ptr r ([ev retain]); + const NSUniquePtr r ([ev retain]); updateKeysDown (ev, true); bool used = handleKeyEvent (ev, true); @@ -838,7 +838,7 @@ public: void redirectModKeyChange (NSEvent* ev) { // (need to retain this in case a modal loop runs and our event object gets lost) - const std::unique_ptr r ([ev retain]); + const NSUniquePtr r ([ev retain]); keysCurrentlyDown.clear(); handleKeyUpOrDown (true); @@ -1242,7 +1242,7 @@ public: String unmodified; #if JUCE_SUPPORT_CARBON - if (TISInputSourceRef currentKeyboard = TISCopyCurrentKeyboardInputSource()) + if (auto currentKeyboard = CFUniquePtr (TISCopyCurrentKeyboardInputSource())) { if (auto layoutData = (CFDataRef) TISGetInputSourceProperty (currentKeyboard, kTISPropertyUnicodeKeyLayoutData)) @@ -1259,8 +1259,6 @@ public: unmodified = String (CharPointer_UTF16 (reinterpret_cast (buffer)), 4); } } - - CFRelease (currentKeyboard); } // did the above layout conversion fail diff --git a/modules/juce_gui_extra/native/juce_ios_PushNotifications.cpp b/modules/juce_gui_extra/native/juce_ios_PushNotifications.cpp index fbccee94d1..b06278ad22 100644 --- a/modules/juce_gui_extra/native/juce_ios_PushNotifications.cpp +++ b/modules/juce_gui_extra/native/juce_ios_PushNotifications.cpp @@ -467,9 +467,9 @@ struct PushNotificationsDelegate protected: #if defined (__IPHONE_10_0) && __IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_10_0 - std::unique_ptr, NSObjectDeleter> delegate; + NSUniquePtr> delegate; #else - std::unique_ptr, NSObjectDeleter> delegate; + NSUniquePtr> delegate; #endif private: diff --git a/modules/juce_gui_extra/native/juce_mac_AppleRemote.mm b/modules/juce_gui_extra/native/juce_mac_AppleRemote.mm index 6aef84355e..812c2902be 100644 --- a/modules/juce_gui_extra/native/juce_mac_AppleRemote.mm +++ b/modules/juce_gui_extra/native/juce_mac_AppleRemote.mm @@ -143,15 +143,15 @@ bool AppleRemoteDevice::open (const bool openInExclusiveMode) { Array cookies; - CFArrayRef elements; + CFObjectHolder elements; auto device122 = (IOHIDDeviceInterface122**) device; - if ((*device122)->copyMatchingElements (device122, nullptr, &elements) != kIOReturnSuccess) + if ((*device122)->copyMatchingElements (device122, nullptr, &elements.object) != kIOReturnSuccess) return false; - for (int i = 0; i < CFArrayGetCount (elements); ++i) + for (int i = 0; i < CFArrayGetCount (elements.object); ++i) { - auto element = (CFDictionaryRef) CFArrayGetValueAtIndex (elements, i); + auto element = (CFDictionaryRef) CFArrayGetValueAtIndex (elements.object, i); // get the cookie CFTypeRef object = CFDictionaryGetValue (element, CFSTR (kIOHIDElementCookieKey)); @@ -166,8 +166,6 @@ bool AppleRemoteDevice::open (const bool openInExclusiveMode) cookies.add ((int) number); } - CFRelease (elements); - if ((*(IOHIDDeviceInterface**) device) ->open ((IOHIDDeviceInterface**) device, openInExclusiveMode ? kIOHIDOptionsTypeSeizeDevice diff --git a/modules/juce_gui_extra/native/juce_mac_PushNotifications.cpp b/modules/juce_gui_extra/native/juce_mac_PushNotifications.cpp index f72d93782a..a868b5f6d1 100644 --- a/modules/juce_gui_extra/native/juce_mac_PushNotifications.cpp +++ b/modules/juce_gui_extra/native/juce_mac_PushNotifications.cpp @@ -298,7 +298,7 @@ struct PushNotificationsDelegate virtual bool shouldPresentNotification (NSUserNotification* notification) = 0; protected: - std::unique_ptr, NSObjectDeleter> delegate; + NSUniquePtr> delegate; private: struct Class : public ObjCClass> diff --git a/modules/juce_gui_extra/native/juce_mac_SystemTrayIcon.cpp b/modules/juce_gui_extra/native/juce_mac_SystemTrayIcon.cpp index f40d166834..4427758c28 100644 --- a/modules/juce_gui_extra/native/juce_mac_SystemTrayIcon.cpp +++ b/modules/juce_gui_extra/native/juce_mac_SystemTrayIcon.cpp @@ -80,8 +80,8 @@ struct StatusItemContainer : public Timer //============================================================================== SystemTrayIconComponent& owner; - std::unique_ptr statusItem; - std::unique_ptr statusIcon; + NSUniquePtr statusItem; + NSUniquePtr statusIcon; JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (StatusItemContainer) }; @@ -201,7 +201,7 @@ struct ButtonBasedStatusItem : public StatusItemContainer }; //============================================================================== - std::unique_ptr eventForwarder; + NSUniquePtr eventForwarder; }; //============================================================================== @@ -368,7 +368,7 @@ struct ViewBasedStatusItem : public StatusItemContainer }; //============================================================================== - std::unique_ptr view; + NSUniquePtr view; bool isHighlighted = false; }; diff --git a/modules/juce_video/native/juce_ios_CameraDevice.h b/modules/juce_video/native/juce_ios_CameraDevice.h index 0c0864533e..cbefc19c4a 100644 --- a/modules/juce_video/native/juce_ios_CameraDevice.h +++ b/modules/juce_video/native/juce_ios_CameraDevice.h @@ -304,11 +304,8 @@ private: static String cmTimeToString (CMTime time) { - CFStringRef timeDesc = CMTimeCopyDescription (nullptr, time); - String result = String::fromCFString (timeDesc); - - CFRelease (timeDesc); - return result; + CFUniquePtr timeDesc (CMTimeCopyDescription (nullptr, time)); + return String::fromCFString (timeDesc.get()); } static String frameRateRangeToString (AVFrameRateRange* range)