0

Rewrite most of the scopers in //base/mac to use ScopedTypeRef or ScopedGeneric.

This removes a lot of duplicated code in favor of using type aliases and
minimal Traits structs.

R=mark@chromium.org

Review URL: https://codereview.chromium.org/1551943002 .

Cr-Commit-Position: refs/heads/master@{#367322}
This commit is contained in:
Robert Sesek
2016-01-04 12:43:00 -05:00
parent 5a60672643
commit cfd6ed5600
21 changed files with 172 additions and 450 deletions

@ -18,7 +18,7 @@ launch_data_t MessageForJob(const std::string& job_label,
const char* operation) {
// launch_data_alloc returns something that needs to be freed.
ScopedLaunchData message(launch_data_alloc(LAUNCH_DATA_DICTIONARY));
if (!message) {
if (!message.is_valid()) {
LOG(ERROR) << "launch_data_alloc";
return NULL;
}
@ -28,38 +28,38 @@ launch_data_t MessageForJob(const std::string& job_label,
// called, so put it in a scoper and .release() it when given to the
// dictionary.
ScopedLaunchData job_label_launchd(launch_data_new_string(job_label.c_str()));
if (!job_label_launchd) {
if (!job_label_launchd.is_valid()) {
LOG(ERROR) << "launch_data_new_string";
return NULL;
}
if (!launch_data_dict_insert(message,
job_label_launchd.release(),
if (!launch_data_dict_insert(message.get(), job_label_launchd.release(),
operation)) {
return NULL;
}
return launch_msg(message);
return launch_msg(message.get());
}
pid_t PIDForJob(const std::string& job_label) {
ScopedLaunchData response(MessageForJob(job_label, LAUNCH_KEY_GETJOB));
if (!response) {
if (!response.is_valid()) {
return -1;
}
launch_data_type_t response_type = launch_data_get_type(response);
launch_data_type_t response_type = launch_data_get_type(response.get());
if (response_type != LAUNCH_DATA_DICTIONARY) {
if (response_type == LAUNCH_DATA_ERRNO) {
LOG(ERROR) << "PIDForJob: error " << launch_data_get_errno(response);
LOG(ERROR) << "PIDForJob: error "
<< launch_data_get_errno(response.get());
} else {
LOG(ERROR) << "PIDForJob: expected dictionary, got " << response_type;
}
return -1;
}
launch_data_t pid_data = launch_data_dict_lookup(response,
LAUNCH_JOBKEY_PID);
launch_data_t pid_data =
launch_data_dict_lookup(response.get(), LAUNCH_JOBKEY_PID);
if (!pid_data)
return 0;

@ -7,83 +7,27 @@
#include <Block.h>
#include "base/compiler_specific.h"
#include "base/memory/scoped_policy.h"
#include "base/mac/scoped_typeref.h"
namespace base {
namespace mac {
namespace internal {
template <typename B>
struct ScopedBlockTraits {
static B InvalidValue() { return nullptr; }
static B Retain(B block) { return Block_copy(block); }
static void Release(B block) { Block_release(block); }
};
} // namespace internal
// ScopedBlock<> is patterned after ScopedCFTypeRef<>, but uses Block_copy() and
// Block_release() instead of CFRetain() and CFRelease().
template<typename B>
class ScopedBlock {
public:
explicit ScopedBlock(
B block = nullptr,
base::scoped_policy::OwnershipPolicy policy = base::scoped_policy::ASSUME)
: block_(block) {
if (block_ && policy == base::scoped_policy::RETAIN)
block_ = Block_copy(block);
}
ScopedBlock(const ScopedBlock<B>& that)
: block_(that.block_) {
if (block_)
block_ = Block_copy(block_);
}
~ScopedBlock() {
if (block_)
Block_release(block_);
}
ScopedBlock& operator=(const ScopedBlock<B>& that) {
reset(that.get(), base::scoped_policy::RETAIN);
return *this;
}
void reset(B block = nullptr,
base::scoped_policy::OwnershipPolicy policy =
base::scoped_policy::ASSUME) {
if (block && policy == base::scoped_policy::RETAIN)
block = Block_copy(block);
if (block_)
Block_release(block_);
block_ = block;
}
bool operator==(B that) const {
return block_ == that;
}
bool operator!=(B that) const {
return block_ != that;
}
operator B() const {
return block_;
}
B get() const {
return block_;
}
void swap(ScopedBlock& that) {
B temp = that.block_;
that.block_ = block_;
block_ = temp;
}
B release() WARN_UNUSED_RESULT {
B temp = block_;
block_ = nullptr;
return temp;
}
private:
B block_;
};
template <typename B>
using ScopedBlock = ScopedTypeRef<B, internal::ScopedBlockTraits<B>>;
} // namespace mac
} // namespace base

@ -7,67 +7,31 @@
#include <CoreFoundation/CoreFoundation.h>
#include "base/compiler_specific.h"
#include "base/macros.h"
#include "base/scoped_generic.h"
namespace base {
namespace mac {
namespace internal {
struct ScopedCFFileDescriptorRefTraits {
static CFFileDescriptorRef InvalidValue() { return nullptr; }
static void Free(CFFileDescriptorRef ref) {
CFFileDescriptorInvalidate(ref);
CFRelease(ref);
}
};
} // namespace internal
// ScopedCFFileDescriptorRef is designed after ScopedCFTypeRef<>. On
// destruction, it will invalidate the file descriptor.
// ScopedCFFileDescriptorRef (unlike ScopedCFTypeRef<>) does not support RETAIN
// semantics, copying, or assignment, as doing so would increase the chances
// that a file descriptor is invalidated while still in use.
class ScopedCFFileDescriptorRef {
public:
explicit ScopedCFFileDescriptorRef(CFFileDescriptorRef fdref = NULL)
: fdref_(fdref) {
}
~ScopedCFFileDescriptorRef() {
if (fdref_) {
CFFileDescriptorInvalidate(fdref_);
CFRelease(fdref_);
}
}
void reset(CFFileDescriptorRef fdref = NULL) {
if (fdref_ == fdref)
return;
if (fdref_) {
CFFileDescriptorInvalidate(fdref_);
CFRelease(fdref_);
}
fdref_ = fdref;
}
bool operator==(CFFileDescriptorRef that) const {
return fdref_ == that;
}
bool operator!=(CFFileDescriptorRef that) const {
return fdref_ != that;
}
operator CFFileDescriptorRef() const {
return fdref_;
}
CFFileDescriptorRef get() const {
return fdref_;
}
CFFileDescriptorRef release() WARN_UNUSED_RESULT {
CFFileDescriptorRef temp = fdref_;
fdref_ = NULL;
return temp;
}
private:
CFFileDescriptorRef fdref_;
DISALLOW_COPY_AND_ASSIGN(ScopedCFFileDescriptorRef);
};
using ScopedCFFileDescriptorRef =
ScopedGeneric<CFFileDescriptorRef,
internal::ScopedCFFileDescriptorRefTraits>;
} // namespace mac
} // namespace base

@ -30,8 +30,9 @@ namespace internal {
template<typename CFT>
struct ScopedCFTypeRefTraits {
static CFT InvalidValue() { return nullptr; }
static void Retain(CFT object) {
static CFT Retain(CFT object) {
CFRetain(object);
return object;
}
static void Release(CFT object) {
CFRelease(object);

@ -7,67 +7,29 @@
#include <IOKit/IOKitLib.h>
#include "base/compiler_specific.h"
#include "base/macros.h"
#include "base/mac/scoped_typeref.h"
namespace base {
namespace mac {
// Just like ScopedCFTypeRef but for io_object_t and subclasses.
template<typename IOT>
class ScopedIOObject {
public:
typedef IOT element_type;
namespace internal {
explicit ScopedIOObject(IOT object = IO_OBJECT_NULL)
: object_(object) {
template <typename IOT>
struct ScopedIOObjectTraits {
static IOT InvalidValue() { return IO_OBJECT_NULL; }
static IOT Retain(IOT iot) {
IOObjectRetain(iot);
return iot;
}
~ScopedIOObject() {
if (object_)
IOObjectRelease(object_);
}
void reset(IOT object = IO_OBJECT_NULL) {
if (object_)
IOObjectRelease(object_);
object_ = object;
}
bool operator==(IOT that) const {
return object_ == that;
}
bool operator!=(IOT that) const {
return object_ != that;
}
operator IOT() const {
return object_;
}
IOT get() const {
return object_;
}
void swap(ScopedIOObject& that) {
IOT temp = that.object_;
that.object_ = object_;
object_ = temp;
}
IOT release() WARN_UNUSED_RESULT {
IOT temp = object_;
object_ = IO_OBJECT_NULL;
return temp;
}
private:
IOT object_;
DISALLOW_COPY_AND_ASSIGN(ScopedIOObject);
static void Release(IOT iot) { IOObjectRelease(iot); }
};
} // namespce internal
// Just like ScopedCFTypeRef but for io_object_t and subclasses.
template <typename IOT>
using ScopedIOObject = ScopedTypeRef<IOT, internal::ScopedIOObjectTraits<IOT>>;
} // namespace mac
} // namespace base

@ -7,68 +7,30 @@
#include <IOKit/IOKitLib.h>
#include "base/compiler_specific.h"
#include "base/macros.h"
#include "base/mac/scoped_typeref.h"
namespace base {
namespace mac {
namespace internal {
template <typename T>
struct ScopedIOPluginInterfaceTraits {
static T InvalidValue() { return nullptr; }
static T Retain(T t) {
(*t)->AddRef(t);
return t;
}
static void Release(T t) { (*t)->Release(t); }
};
} // namespace internal
// Just like ScopedCFTypeRef but for IOCFPlugInInterface and friends
// (IOUSBInterfaceStruct and IOUSBDeviceStruct320 in particular).
template<typename T>
class ScopedIOPluginInterface {
public:
typedef T** InterfaceT;
typedef InterfaceT element_type;
explicit ScopedIOPluginInterface(InterfaceT object = NULL)
: object_(object) {
}
~ScopedIOPluginInterface() {
if (object_)
(*object_)->Release(object_);
}
void reset(InterfaceT object = NULL) {
if (object_)
(*object_)->Release(object_);
object_ = object;
}
bool operator==(InterfaceT that) const {
return object_ == that;
}
bool operator!=(InterfaceT that) const {
return object_ != that;
}
operator InterfaceT() const {
return object_;
}
InterfaceT get() const {
return object_;
}
void swap(ScopedIOPluginInterface& that) {
InterfaceT temp = that.object_;
that.object_ = object_;
object_ = temp;
}
InterfaceT release() WARN_UNUSED_RESULT {
InterfaceT temp = object_;
object_ = NULL;
return temp;
}
private:
InterfaceT object_;
DISALLOW_COPY_AND_ASSIGN(ScopedIOPluginInterface);
};
template <typename T>
using ScopedIOPluginInterface =
ScopedTypeRef<T**, internal::ScopedIOPluginInterfaceTraits<T**>>;
} // namespace mac
} // namespace base

@ -7,68 +7,24 @@
#include <launch.h>
#include <algorithm>
#include "base/compiler_specific.h"
#include "base/macros.h"
#include "base/scoped_generic.h"
namespace base {
namespace mac {
// Just like scoped_ptr<> but for launch_data_t.
class ScopedLaunchData {
public:
typedef launch_data_t element_type;
namespace internal {
explicit ScopedLaunchData(launch_data_t object = NULL)
: object_(object) {
}
~ScopedLaunchData() {
if (object_)
launch_data_free(object_);
}
void reset(launch_data_t object = NULL) {
if (object != object_) {
if (object_)
launch_data_free(object_);
object_ = object;
}
}
bool operator==(launch_data_t that) const {
return object_ == that;
}
bool operator!=(launch_data_t that) const {
return object_ != that;
}
operator launch_data_t() const {
return object_;
}
launch_data_t get() const {
return object_;
}
void swap(ScopedLaunchData& that) {
std::swap(object_, that.object_);
}
launch_data_t release() WARN_UNUSED_RESULT {
launch_data_t temp = object_;
object_ = NULL;
return temp;
}
private:
launch_data_t object_;
DISALLOW_COPY_AND_ASSIGN(ScopedLaunchData);
struct ScopedLaunchDataTraits {
static launch_data_t InvalidValue() { return nullptr; }
static void Free(launch_data_t ldt) { launch_data_free(ldt); }
};
} // namespace internal
// Just like scoped_ptr<> but for launch_data_t.
using ScopedLaunchData =
ScopedGeneric<launch_data_t, internal::ScopedLaunchDataTraits>;
} // namespace mac
} // namespace base

@ -5,13 +5,15 @@
#ifndef BASE_MAC_SCOPED_NSOBJECT_H_
#define BASE_MAC_SCOPED_NSOBJECT_H_
#include <type_traits>
// Include NSObject.h directly because Foundation.h pulls in many dependencies.
// (Approx 100k lines of code versus 1.5k for NSObject.h). scoped_nsobject gets
// singled out because it is most typically included from other header files.
#import <Foundation/NSObject.h>
#include "base/compiler_specific.h"
#include "base/macros.h"
#include "base/mac/scoped_typeref.h"
@class NSAutoreleasePool;
@ -37,71 +39,26 @@ namespace base {
// We check for bad uses of scoped_nsobject and NSAutoreleasePool at compile
// time with a template specialization (see below).
template<typename NST>
class scoped_nsprotocol {
namespace internal {
template <typename NST>
struct ScopedNSProtocolTraits {
static NST InvalidValue() { return nil; }
static NST Retain(NST nst) { return [nst retain]; }
static void Release(NST nst) { [nst release]; }
};
} // namespace internal
template <typename NST>
class scoped_nsprotocol
: public ScopedTypeRef<NST, internal::ScopedNSProtocolTraits<NST>> {
public:
explicit scoped_nsprotocol(NST object = nil) : object_(object) {}
scoped_nsprotocol(const scoped_nsprotocol<NST>& that)
: object_([that.object_ retain]) {
}
template <typename NSU>
scoped_nsprotocol(const scoped_nsprotocol<NSU>& that)
: object_([that.get() retain]) {
}
~scoped_nsprotocol() {
[object_ release];
}
scoped_nsprotocol& operator=(const scoped_nsprotocol<NST>& that) {
reset([that.get() retain]);
return *this;
}
void reset(NST object = nil) {
// We intentionally do not check that object != object_ as the caller must
// either already have an ownership claim over whatever it passes to this
// method, or call it with the |RETAIN| policy which will have ensured that
// the object is retained once more when reaching this point.
[object_ release];
object_ = object;
}
bool operator==(NST that) const { return object_ == that; }
bool operator!=(NST that) const { return object_ != that; }
operator NST() const {
return object_;
}
NST get() const {
return object_;
}
void swap(scoped_nsprotocol& that) {
NST temp = that.object_;
that.object_ = object_;
object_ = temp;
}
// scoped_nsprotocol<>::release() is like scoped_ptr<>::release. It is NOT a
// wrapper for [object_ release]. To force a scoped_nsprotocol<> to call
// [object_ release], use scoped_nsprotocol<>::reset().
NST release() WARN_UNUSED_RESULT {
NST temp = object_;
object_ = nil;
return temp;
}
using ScopedTypeRef<NST,
internal::ScopedNSProtocolTraits<NST>>::ScopedTypeRef;
// Shift reference to the autorelease pool to be released later.
NST autorelease() {
return [release() autorelease];
}
private:
NST object_;
NST autorelease() { return [this->release() autorelease]; }
};
// Free functions
@ -120,56 +77,20 @@ bool operator!=(C p1, const scoped_nsprotocol<C>& p2) {
return p1 != p2.get();
}
template<typename NST>
template <typename NST>
class scoped_nsobject : public scoped_nsprotocol<NST*> {
public:
explicit scoped_nsobject(NST* object = nil)
: scoped_nsprotocol<NST*>(object) {}
using scoped_nsprotocol<NST*>::scoped_nsprotocol;
scoped_nsobject(const scoped_nsobject<NST>& that)
: scoped_nsprotocol<NST*>(that) {
}
template<typename NSU>
scoped_nsobject(const scoped_nsobject<NSU>& that)
: scoped_nsprotocol<NST*>(that) {
}
scoped_nsobject& operator=(const scoped_nsobject<NST>& that) {
scoped_nsprotocol<NST*>::operator=(that);
return *this;
}
static_assert(std::is_same<NST, NSAutoreleasePool>::value == false,
"Use ScopedNSAutoreleasePool instead");
};
// Specialization to make scoped_nsobject<id> work.
template<>
class scoped_nsobject<id> : public scoped_nsprotocol<id> {
public:
explicit scoped_nsobject(id object = nil) : scoped_nsprotocol<id>(object) {}
scoped_nsobject(const scoped_nsobject<id>& that)
: scoped_nsprotocol<id>(that) {
}
template<typename NSU>
scoped_nsobject(const scoped_nsobject<NSU>& that)
: scoped_nsprotocol<id>(that) {
}
scoped_nsobject& operator=(const scoped_nsobject<id>& that) {
scoped_nsprotocol<id>::operator=(that);
return *this;
}
};
// Do not use scoped_nsobject for NSAutoreleasePools, use
// ScopedNSAutoreleasePool instead. This is a compile time check. See details
// at top of header.
template<>
class scoped_nsobject<NSAutoreleasePool> {
private:
explicit scoped_nsobject(NSAutoreleasePool* object = nil);
DISALLOW_COPY_AND_ASSIGN(scoped_nsobject);
using scoped_nsprotocol<id>::scoped_nsprotocol;
};
} // namespace base

@ -52,6 +52,12 @@ TEST(ScopedNSObjectTest, ScopedNSObject) {
ASSERT_EQ(2u, [p1 retainCount]);
}
#if 0
TEST(ScopedNSObjectTest, FailToCreateScopedNSObjectAutoreleasePool) {
base::scoped_nsobject<NSAutoreleasePool> pool;
}
#endif
TEST(ScopedNSObjectTest, ScopedNSObjectInContainer) {
base::scoped_nsobject<id> p([[NSObject alloc] init]);
ASSERT_TRUE(p.get());

@ -22,7 +22,10 @@ namespace base {
// template<>
// struct ScopedTypeRefTraits<CGLContextObj> {
// static CGLContextObj InvalidValue() { return nullptr; }
// static void Retain(CGLContextObj object) { CGLContextRetain(object); }
// static CGLContextObj Retain(CGLContextObj object) {
// CGLContextRetain(object);
// return object;
// }
// static void Release(CGLContextObj object) { CGLContextRelease(object); }
// };
//
@ -55,13 +58,13 @@ class ScopedTypeRef {
base::scoped_policy::OwnershipPolicy policy = base::scoped_policy::ASSUME)
: object_(object) {
if (object_ && policy == base::scoped_policy::RETAIN)
Traits::Retain(object_);
object_ = Traits::Retain(object_);
}
ScopedTypeRef(const ScopedTypeRef<T, Traits>& that)
: object_(that.object_) {
if (object_)
Traits::Retain(object_);
object_ = Traits::Retain(object_);
}
~ScopedTypeRef() {
@ -86,7 +89,7 @@ class ScopedTypeRef {
base::scoped_policy::OwnershipPolicy policy =
base::scoped_policy::ASSUME) {
if (object && policy == base::scoped_policy::RETAIN)
Traits::Retain(object);
object = Traits::Retain(object);
if (object_)
Traits::Release(object_);
object_ = object;

@ -22,7 +22,7 @@ bool MessagePumpIOSForIO::FileDescriptorWatcher::StopWatchingFileDescriptor() {
if (fdref_ == NULL)
return true;
CFFileDescriptorDisableCallBacks(fdref_, callback_types_);
CFFileDescriptorDisableCallBacks(fdref_.get(), callback_types_);
if (pump_)
pump_->RemoveRunLoopSource(fd_source_);
fd_source_.reset();
@ -39,7 +39,7 @@ void MessagePumpIOSForIO::FileDescriptorWatcher::Init(
CFRunLoopSourceRef fd_source,
bool is_persistent) {
DCHECK(fdref);
DCHECK(!fdref_);
DCHECK(!fdref_.is_valid());
is_persistent_ = is_persistent;
fdref_.reset(fdref);
@ -97,7 +97,7 @@ bool MessagePumpIOSForIO::WatchFileDescriptor(
callback_types |= kCFFileDescriptorWriteCallBack;
}
CFFileDescriptorRef fdref = controller->fdref_;
CFFileDescriptorRef fdref = controller->fdref_.get();
if (fdref == NULL) {
base::ScopedCFTypeRef<CFFileDescriptorRef> scoped_fdref(
CFFileDescriptorCreate(
@ -174,7 +174,7 @@ void MessagePumpIOSForIO::HandleFdIOEvent(CFFileDescriptorRef fdref,
void* context) {
FileDescriptorWatcher* controller =
static_cast<FileDescriptorWatcher*>(context);
DCHECK_EQ(fdref, controller->fdref_);
DCHECK_EQ(fdref, controller->fdref_.get());
// Ensure that |fdref| will remain live for the duration of this function
// call even if |controller| is deleted or |StopWatchingFileDescriptor()| is
@ -194,14 +194,14 @@ void MessagePumpIOSForIO::HandleFdIOEvent(CFFileDescriptorRef fdref,
// guarantees that |controller| has not been deleted.
if (callback_types & kCFFileDescriptorReadCallBack &&
CFFileDescriptorIsValid(fdref)) {
DCHECK_EQ(fdref, controller->fdref_);
DCHECK_EQ(fdref, controller->fdref_.get());
controller->OnFileCanReadWithoutBlocking(fd, pump);
}
// Re-enable callbacks after the read/write if the file descriptor is still
// valid and the controller is persistent.
if (CFFileDescriptorIsValid(fdref) && controller->is_persistent_) {
DCHECK_EQ(fdref, controller->fdref_);
DCHECK_EQ(fdref, controller->fdref_.get());
CFFileDescriptorEnableCallBacks(fdref, callback_types);
}
}

@ -44,7 +44,7 @@ class MessagePumpIOSForIOTest : public testing::Test {
}
void HandleFdIOEvent(MessageLoopForIO::FileDescriptorWatcher* watcher) {
MessagePumpIOSForIO::HandleFdIOEvent(watcher->fdref_,
MessagePumpIOSForIO::HandleFdIOEvent(watcher->fdref_.get(),
kCFFileDescriptorReadCallBack | kCFFileDescriptorWriteCallBack,
watcher);
}

@ -139,7 +139,8 @@ TEST_F(ServiceDiscoveryClientMacTest, ServiceResolver) {
ServiceResolverImplMac* resolver_impl =
static_cast<ServiceResolverImplMac*>(resolver.get());
resolver_impl->GetContainerForTesting()->SetServiceForTesting(test_service);
resolver_impl->GetContainerForTesting()->SetServiceForTesting(
test_service.release());
resolver->StartResolving();
resolver_impl->GetContainerForTesting()->OnResolveUpdate(

@ -375,8 +375,7 @@ static const NSTimeInterval kAnimationContinuousCycleDuration = 0.4;
// The basic gradient shown inside; see above.
NSGradient* gradient;
if (hoverAlpha == 0 && !useThemeGradient) {
gradient = defaultGradient ? defaultGradient
: gradient_;
gradient = defaultGradient ? defaultGradient : gradient_.get();
} else {
gradient = [self gradientForHoverAlpha:hoverAlpha
isThemed:useThemeGradient];

@ -94,11 +94,11 @@ MEDIA_EXPORT
@end
MEDIA_EXPORT
@interface CrAVCaptureInput // Originally from AVCaptureInput.h.
@interface CrAVCaptureInput : NSObject // Originally from AVCaptureInput.h.
@end
MEDIA_EXPORT
@interface CrAVCaptureOutput // Originally from AVCaptureOutput.h.
@interface CrAVCaptureOutput : NSObject // Originally from AVCaptureOutput.h.
@end
// Originally AVCaptureSession and coming from AVCaptureSession.h.

@ -64,7 +64,7 @@ launch_data_t MessageForJob(const std::string& job_label,
const char* operation) {
// launch_data_alloc returns something that needs to be freed.
ScopedLaunchData message(launch_data_alloc(LAUNCH_DATA_DICTIONARY));
if (!message) {
if (!message.is_valid()) {
NSLog(@"launch_data_alloc");
return nullptr;
}
@ -74,37 +74,37 @@ launch_data_t MessageForJob(const std::string& job_label,
// called, so put it in a scoper and .release() it when given to the
// dictionary.
ScopedLaunchData job_label_launchd(launch_data_new_string(job_label.c_str()));
if (!job_label_launchd) {
if (!job_label_launchd.is_valid()) {
NSLog(@"launch_data_new_string");
return nullptr;
}
if (!launch_data_dict_insert(message,
if (!launch_data_dict_insert(message.get(),
job_label_launchd.release(),
operation)) {
return nullptr;
}
return launch_msg(message);
return launch_msg(message.get());
}
pid_t PIDForJob(const std::string& job_label) {
ScopedLaunchData response(MessageForJob(job_label, LAUNCH_KEY_GETJOB));
if (!response) {
if (!response.is_valid()) {
return -1;
}
launch_data_type_t response_type = launch_data_get_type(response);
launch_data_type_t response_type = launch_data_get_type(response.get());
if (response_type != LAUNCH_DATA_DICTIONARY) {
if (response_type == LAUNCH_DATA_ERRNO) {
NSLog(@"PIDForJob: error %d", launch_data_get_errno(response));
NSLog(@"PIDForJob: error %d", launch_data_get_errno(response.get()));
} else {
NSLog(@"PIDForJob: expected dictionary, got %d", response_type);
}
return -1;
}
launch_data_t pid_data = launch_data_dict_lookup(response,
launch_data_t pid_data = launch_data_dict_lookup(response.get(),
LAUNCH_JOBKEY_PID);
if (!pid_data)
return 0;
@ -583,7 +583,7 @@ std::string JsonHostConfig::GetSerializedData() const {
- (BOOL)sendJobControlMessage:(const char*)launch_key {
base::mac::ScopedLaunchData response(
base::mac::MessageForJob(remoting::kServiceName, launch_key));
if (!response) {
if (!response.is_valid()) {
NSLog(@"Failed to send message to launchd");
[self showError];
return NO;

@ -37,3 +37,5 @@ $ git am --3way --message-id -p4 /tmp/patchdir
Local Modifications:
- Removed references to "base/basictypes.h" and replaced them with appropriate
headers.
- Updated usage of ScopedLaunchData to use explicit methods rather than the
implicit |operator T()| conversion.

@ -51,7 +51,8 @@ launch_data_t CFPropertyToLaunchData(CFPropertyListRef property_cf) {
return nullptr;
}
LaunchDataDictInsert(dictionary_launch, value_launch, [key UTF8String]);
LaunchDataDictInsert(
dictionary_launch.get(), value_launch, [key UTF8String]);
}
data_launch = dictionary_launch.release();
@ -71,7 +72,7 @@ launch_data_t CFPropertyToLaunchData(CFPropertyListRef property_cf) {
return nullptr;
}
LaunchDataArraySetIndex(array_launch, element_launch, index++);
LaunchDataArraySetIndex(array_launch.get(), element_launch, index++);
}
data_launch = array_launch.release();

@ -28,10 +28,10 @@ namespace {
launch_data_t LaunchDataDictionaryForJob(const std::string& label) {
base::mac::ScopedLaunchData request(LaunchDataAlloc(LAUNCH_DATA_DICTIONARY));
LaunchDataDictInsert(
request, LaunchDataNewString(label.c_str()), LAUNCH_KEY_GETJOB);
request.get(), LaunchDataNewString(label.c_str()), LAUNCH_KEY_GETJOB);
base::mac::ScopedLaunchData response(LaunchMsg(request));
if (LaunchDataGetType(response) != LAUNCH_DATA_DICTIONARY) {
base::mac::ScopedLaunchData response(LaunchMsg(request.get()));
if (LaunchDataGetType(response.get()) != LAUNCH_DATA_DICTIONARY) {
return nullptr;
}
@ -47,21 +47,21 @@ bool ServiceManagementSubmitJob(CFDictionaryRef job_cf) {
}
base::mac::ScopedLaunchData jobs(LaunchDataAlloc(LAUNCH_DATA_ARRAY));
LaunchDataArraySetIndex(jobs, job_launch.release(), 0);
LaunchDataArraySetIndex(jobs.get(), job_launch.release(), 0);
base::mac::ScopedLaunchData request(LaunchDataAlloc(LAUNCH_DATA_DICTIONARY));
LaunchDataDictInsert(request, jobs.release(), LAUNCH_KEY_SUBMITJOB);
LaunchDataDictInsert(request.get(), jobs.release(), LAUNCH_KEY_SUBMITJOB);
base::mac::ScopedLaunchData response(LaunchMsg(request));
if (LaunchDataGetType(response) != LAUNCH_DATA_ARRAY) {
base::mac::ScopedLaunchData response(LaunchMsg(request.get()));
if (LaunchDataGetType(response.get()) != LAUNCH_DATA_ARRAY) {
return false;
}
if (LaunchDataArrayGetCount(response) != 1) {
if (LaunchDataArrayGetCount(response.get()) != 1) {
return false;
}
launch_data_t response_element = LaunchDataArrayGetIndex(response, 0);
launch_data_t response_element = LaunchDataArrayGetIndex(response.get(), 0);
if (LaunchDataGetType(response_element) != LAUNCH_DATA_ERRNO) {
return false;
}
@ -77,14 +77,14 @@ bool ServiceManagementSubmitJob(CFDictionaryRef job_cf) {
bool ServiceManagementRemoveJob(const std::string& label, bool wait) {
base::mac::ScopedLaunchData request(LaunchDataAlloc(LAUNCH_DATA_DICTIONARY));
LaunchDataDictInsert(
request, LaunchDataNewString(label.c_str()), LAUNCH_KEY_REMOVEJOB);
request.get(), LaunchDataNewString(label.c_str()), LAUNCH_KEY_REMOVEJOB);
base::mac::ScopedLaunchData response(LaunchMsg(request));
if (LaunchDataGetType(response) != LAUNCH_DATA_ERRNO) {
base::mac::ScopedLaunchData response(LaunchMsg(request.get()));
if (LaunchDataGetType(response.get()) != LAUNCH_DATA_ERRNO) {
return false;
}
int err = LaunchDataGetErrno(response);
int err = LaunchDataGetErrno(response.get());
if (err == EINPROGRESS) {
if (wait) {
// TODO(mark): Use a kqueue to wait for the process to exit. To avoid a
@ -108,7 +108,7 @@ bool ServiceManagementRemoveJob(const std::string& label, bool wait) {
bool ServiceManagementIsJobLoaded(const std::string& label) {
base::mac::ScopedLaunchData dictionary(LaunchDataDictionaryForJob(label));
if (!dictionary) {
if (!dictionary.is_valid()) {
return false;
}
@ -117,11 +117,11 @@ bool ServiceManagementIsJobLoaded(const std::string& label) {
pid_t ServiceManagementIsJobRunning(const std::string& label) {
base::mac::ScopedLaunchData dictionary(LaunchDataDictionaryForJob(label));
if (!dictionary) {
if (!dictionary.is_valid()) {
return 0;
}
launch_data_t pid = LaunchDataDictLookup(dictionary, LAUNCH_JOBKEY_PID);
launch_data_t pid = LaunchDataDictLookup(dictionary.get(), LAUNCH_JOBKEY_PID);
if (!pid) {
return 0;
}

@ -15,8 +15,8 @@ namespace base {
template<>
struct ScopedTypeRefTraits<CVDisplayLinkRef> {
static CVDisplayLinkRef InvalidValue() { return nullptr; }
static void Retain(CVDisplayLinkRef object) {
CVDisplayLinkRetain(object);
static CVDisplayLinkRef Retain(CVDisplayLinkRef object) {
return CVDisplayLinkRetain(object);
}
static void Release(CVDisplayLinkRef object) {
CVDisplayLinkRelease(object);

@ -16,8 +16,8 @@ namespace base {
template<>
struct ScopedTypeRefTraits<CGLContextObj> {
static CGLContextObj InvalidValue() { return nullptr; }
static void Retain(CGLContextObj object) {
CGLRetainContext(object);
static CGLContextObj Retain(CGLContextObj object) {
return CGLRetainContext(object);
}
static void Release(CGLContextObj object) {
CGLReleaseContext(object);
@ -27,8 +27,8 @@ struct ScopedTypeRefTraits<CGLContextObj> {
template<>
struct ScopedTypeRefTraits<CGLPixelFormatObj> {
static CGLPixelFormatObj InvalidValue() { return nullptr; }
static void Retain(CGLPixelFormatObj object) {
CGLRetainPixelFormat(object);
static CGLPixelFormatObj Retain(CGLPixelFormatObj object) {
return CGLRetainPixelFormat(object);
}
static void Release(CGLPixelFormatObj object) {
CGLReleasePixelFormat(object);