Skip to content

Commit 8529a36

Browse files
authored
Merge pull request #120 from madsmtm/smart-msg-send
Add `msg_send_id!` to help with following memory management rules
2 parents b867157 + 726c660 commit 8529a36

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

44 files changed

+1692
-254
lines changed

objc2-foundation/examples/class_with_lifetime.rs

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ use std::sync::Once;
55
use objc2::declare::ClassBuilder;
66
use objc2::rc::{Id, Owned, Shared};
77
use objc2::runtime::{Class, Object, Sel};
8-
use objc2::{msg_send, sel};
8+
use objc2::{msg_send, msg_send_id, sel};
99
use objc2::{Encoding, Message, RefEncode};
1010
use objc2_foundation::NSObject;
1111

@@ -28,9 +28,8 @@ static MYOBJECT_REGISTER_CLASS: Once = Once::new();
2828
impl<'a> MyObject<'a> {
2929
fn new(number_ptr: &'a mut u8) -> Id<Self, Owned> {
3030
unsafe {
31-
let obj: *mut Self = msg_send![Self::class(), alloc];
32-
let obj: *mut Self = msg_send![obj, initWithPtr: number_ptr];
33-
Id::new(obj).unwrap()
31+
let obj = msg_send_id![Self::class(), alloc];
32+
msg_send_id![obj, initWithPtr: number_ptr].unwrap()
3433
}
3534
}
3635

objc2-foundation/examples/custom_class.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ use std::sync::Once;
33
use objc2::declare::ClassBuilder;
44
use objc2::rc::{Id, Owned};
55
use objc2::runtime::{Class, Object, Sel};
6-
use objc2::{msg_send, sel};
6+
use objc2::{msg_send, msg_send_id, sel};
77
use objc2::{Encoding, Message, RefEncode};
88
use objc2_foundation::NSObject;
99

@@ -25,7 +25,7 @@ static MYOBJECT_REGISTER_CLASS: Once = Once::new();
2525
impl MYObject {
2626
fn new() -> Id<Self, Owned> {
2727
let cls = Self::class();
28-
unsafe { Id::new(msg_send![cls, new]).unwrap() }
28+
unsafe { msg_send_id![cls, new].unwrap() }
2929
}
3030

3131
fn number(&self) -> u32 {

objc2-foundation/src/attributed_string.rs

Lines changed: 7 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
1-
use objc2::msg_send;
21
use objc2::rc::{DefaultId, Id, Shared};
32
use objc2::runtime::Object;
3+
use objc2::{msg_send, msg_send_id};
44

55
use crate::{
66
NSCopying, NSDictionary, NSMutableAttributedString, NSMutableCopying, NSObject, NSString,
@@ -47,28 +47,26 @@ impl NSAttributedString {
4747
attributes: &NSDictionary<NSAttributedStringKey, Object>,
4848
) -> Id<Self, Shared> {
4949
unsafe {
50-
let obj: *mut Self = msg_send![Self::class(), alloc];
51-
let obj: *mut Self = msg_send![obj, initWithString: string, attributes: attributes];
52-
Id::new(obj).unwrap()
50+
let obj = msg_send_id![Self::class(), alloc];
51+
msg_send_id![obj, initWithString: string, attributes: attributes].unwrap()
5352
}
5453
}
5554

5655
/// Creates a new attributed string without any attributes.
5756
#[doc(alias = "initWithString:")]
5857
pub fn from_nsstring(string: &NSString) -> Id<Self, Shared> {
5958
unsafe {
60-
let obj: *mut Self = msg_send![Self::class(), alloc];
61-
let obj: *mut Self = msg_send![obj, initWithString: string];
62-
Id::new(obj).unwrap()
59+
let obj = msg_send_id![Self::class(), alloc];
60+
msg_send_id![obj, initWithString: string].unwrap()
6361
}
6462
}
6563
}
6664

6765
/// Querying.
6866
impl NSAttributedString {
6967
// TODO: Lifetimes?
70-
pub fn string(&self) -> &NSString {
71-
unsafe { msg_send![self, string] }
68+
pub fn string(&self) -> Id<NSString, Shared> {
69+
unsafe { msg_send_id![self, string].unwrap() }
7270
}
7371

7472
/// Alias for `self.string().len_utf16()`.

objc2-foundation/src/copying.rs

Lines changed: 3 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
use objc2::rc::{Id, Owned, Ownership};
2-
use objc2::{msg_send, Message};
2+
use objc2::{msg_send_id, Message};
33

44
pub unsafe trait NSCopying: Message {
55
/// Indicates whether the type is mutable or immutable.
@@ -31,10 +31,7 @@ pub unsafe trait NSCopying: Message {
3131
type Output: Message;
3232

3333
fn copy(&self) -> Id<Self::Output, Self::Ownership> {
34-
unsafe {
35-
let obj: *mut Self::Output = msg_send![self, copy];
36-
Id::new(obj).unwrap()
37-
}
34+
unsafe { msg_send_id![self, copy].unwrap() }
3835
}
3936
}
4037

@@ -46,9 +43,6 @@ pub unsafe trait NSMutableCopying: Message {
4643
type Output: Message;
4744

4845
fn mutable_copy(&self) -> Id<Self::Output, Owned> {
49-
unsafe {
50-
let obj: *mut Self::Output = msg_send![self, mutableCopy];
51-
Id::new(obj).unwrap()
52-
}
46+
unsafe { msg_send_id![self, mutableCopy].unwrap() }
5347
}
5448
}

objc2-foundation/src/data.rs

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,9 @@ use core::ops::{Index, IndexMut, Range};
55
use core::slice::{self, SliceIndex};
66
use std::io;
77

8-
use objc2::msg_send;
98
use objc2::rc::{DefaultId, Id, Owned, Shared};
109
use objc2::runtime::{Class, Object};
10+
use objc2::{msg_send, msg_send_id};
1111

1212
use super::{NSCopying, NSMutableCopying, NSObject, NSRange};
1313

@@ -147,18 +147,16 @@ impl NSMutableData {
147147
pub fn from_data(data: &NSData) -> Id<Self, Owned> {
148148
// Not provided on NSData, one should just use NSData::copy or similar
149149
unsafe {
150-
let obj: *mut Self = msg_send![Self::class(), alloc];
151-
let obj: *mut Self = msg_send![obj, initWithData: data];
152-
Id::new(obj).unwrap()
150+
let obj = msg_send_id![Self::class(), alloc];
151+
msg_send_id![obj, initWithData: data].unwrap()
153152
}
154153
}
155154

156155
#[doc(alias = "initWithCapacity:")]
157156
pub fn with_capacity(capacity: usize) -> Id<Self, Owned> {
158157
unsafe {
159-
let obj: *mut Self = msg_send![Self::class(), alloc];
160-
let obj: *mut Self = msg_send![obj, initWithCapacity: capacity];
161-
Id::new(obj).unwrap()
158+
let obj = msg_send_id![Self::class(), alloc];
159+
msg_send_id![obj, initWithCapacity: capacity].unwrap()
162160
}
163161
}
164162
}

objc2-foundation/src/dictionary.rs

Lines changed: 8 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ use core::ops::Index;
55
use core::ptr;
66

77
use objc2::rc::{DefaultId, Id, Owned, Shared, SliceId};
8-
use objc2::{msg_send, Message};
8+
use objc2::{msg_send, msg_send_id, Message};
99

1010
use super::{NSArray, NSCopying, NSEnumerator, NSFastEnumeration, NSObject};
1111

@@ -101,10 +101,7 @@ impl<K: Message, V: Message> NSDictionary<K, V> {
101101
}
102102

103103
pub fn keys_array(&self) -> Id<NSArray<K, Shared>, Shared> {
104-
unsafe {
105-
let keys = msg_send![self, allKeys];
106-
Id::retain_autoreleased(keys).unwrap()
107-
}
104+
unsafe { msg_send_id![self, allKeys] }.unwrap()
108105
}
109106

110107
pub fn from_keys_and_objects<T>(keys: &[&T], vals: Vec<Id<V, Owned>>) -> Id<Self, Shared>
@@ -115,23 +112,20 @@ impl<K: Message, V: Message> NSDictionary<K, V> {
115112

116113
let cls = Self::class();
117114
let count = min(keys.len(), vals.len());
118-
let obj: *mut Self = unsafe { msg_send![cls, alloc] };
119-
let obj: *mut Self = unsafe {
120-
msg_send![
115+
let obj = unsafe { msg_send_id![cls, alloc] };
116+
unsafe {
117+
msg_send_id![
121118
obj,
122119
initWithObjects: vals.as_ptr(),
123120
forKeys: keys.as_ptr(),
124121
count: count,
125122
]
126-
};
127-
unsafe { Id::new(obj).unwrap() }
123+
}
124+
.unwrap()
128125
}
129126

130127
pub fn into_values_array(dict: Id<Self, Owned>) -> Id<NSArray<V, Owned>, Shared> {
131-
unsafe {
132-
let vals = msg_send![&dict, allValues];
133-
Id::retain_autoreleased(vals).unwrap()
134-
}
128+
unsafe { msg_send_id![&dict, allValues] }.unwrap()
135129
}
136130
}
137131

objc2-foundation/src/macros.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -227,7 +227,7 @@ macro_rules! unsafe_def_fn {
227227
$(#[$m])*
228228
$v fn new() -> Id<Self, $o> {
229229
let cls = Self::class();
230-
unsafe { Id::new(msg_send![cls, new]).unwrap() }
230+
unsafe { ::objc2::msg_send_id![cls, new].unwrap() }
231231
}
232232
};
233233
}

objc2-foundation/src/mutable_attributed_string.rs

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
1-
use objc2::msg_send;
21
use objc2::rc::{DefaultId, Id, Owned, Shared};
2+
use objc2::{msg_send, msg_send_id};
33

44
use crate::{NSAttributedString, NSCopying, NSMutableCopying, NSObject, NSString};
55

@@ -26,18 +26,16 @@ impl NSMutableAttributedString {
2626
#[doc(alias = "initWithString:")]
2727
pub fn from_nsstring(string: &NSString) -> Id<Self, Owned> {
2828
unsafe {
29-
let obj: *mut Self = msg_send![Self::class(), alloc];
30-
let obj: *mut Self = msg_send![obj, initWithString: string];
31-
Id::new(obj).unwrap()
29+
let obj = msg_send_id![Self::class(), alloc];
30+
msg_send_id![obj, initWithString: string].unwrap()
3231
}
3332
}
3433

3534
#[doc(alias = "initWithAttributedString:")]
3635
pub fn from_attributed_nsstring(attributed_string: &NSAttributedString) -> Id<Self, Owned> {
3736
unsafe {
38-
let obj: *mut Self = msg_send![Self::class(), alloc];
39-
let obj: *mut Self = msg_send![obj, initWithAttributedString: attributed_string];
40-
Id::new(obj).unwrap()
37+
let obj = msg_send_id![Self::class(), alloc];
38+
msg_send_id![obj, initWithAttributedString: attributed_string].unwrap()
4139
}
4240
}
4341
}

objc2-foundation/src/mutable_string.rs

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@ use core::fmt;
33
use core::ops::AddAssign;
44
use core::str;
55

6-
use objc2::msg_send;
76
use objc2::rc::{DefaultId, Id, Owned, Shared};
7+
use objc2::{msg_send, msg_send_id};
88

99
use crate::{NSCopying, NSMutableCopying, NSObject, NSString};
1010

@@ -39,18 +39,16 @@ impl NSMutableString {
3939
#[doc(alias = "initWithString:")]
4040
pub fn from_nsstring(string: &NSString) -> Id<Self, Owned> {
4141
unsafe {
42-
let obj: *mut Self = msg_send![Self::class(), alloc];
43-
let obj: *mut Self = msg_send![obj, initWithString: string];
44-
Id::new(obj).unwrap()
42+
let obj = msg_send_id![Self::class(), alloc];
43+
msg_send_id![obj, initWithString: string].unwrap()
4544
}
4645
}
4746

4847
#[doc(alias = "initWithCapacity:")]
4948
pub fn with_capacity(capacity: usize) -> Id<Self, Owned> {
5049
unsafe {
51-
let obj: *mut Self = msg_send![Self::class(), alloc];
52-
let obj: *mut Self = msg_send![obj, initWithCapacity: capacity];
53-
Id::new(obj).unwrap()
50+
let obj = msg_send_id![Self::class(), alloc];
51+
msg_send_id![obj, initWithCapacity: capacity].unwrap()
5452
}
5553
}
5654
}

objc2-foundation/src/object.rs

Lines changed: 3 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
use objc2::rc::{DefaultId, Id, Owned, Shared};
22
use objc2::runtime::{Class, Object};
3-
use objc2::{msg_send, msg_send_bool};
3+
use objc2::{msg_send, msg_send_bool, msg_send_id};
44

55
use super::NSString;
66

@@ -21,11 +21,8 @@ impl NSObject {
2121
}
2222

2323
pub fn description(&self) -> Id<NSString, Shared> {
24-
unsafe {
25-
let result: *mut NSString = msg_send![self, description];
26-
// TODO: Verify that description always returns a non-null string
27-
Id::retain_autoreleased(result).unwrap()
28-
}
24+
// TODO: Verify that description always returns a non-null string
25+
unsafe { msg_send_id![self, description].unwrap() }
2926
}
3027

3128
pub fn is_kind_of(&self, cls: &Class) -> bool {

objc2-foundation/src/process_info.rs

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
use objc2::msg_send;
1+
use objc2::msg_send_id;
22
use objc2::rc::{Id, Shared};
33

44
use crate::{NSObject, NSString};
@@ -20,13 +20,11 @@ unsafe impl Sync for NSProcessInfo {}
2020
impl NSProcessInfo {
2121
pub fn process_info() -> Id<NSProcessInfo, Shared> {
2222
// currentThread is @property(strong), what does that mean?
23-
let obj: *mut Self = unsafe { msg_send![Self::class(), processInfo] };
2423
// TODO: Always available?
25-
unsafe { Id::retain_autoreleased(obj).unwrap() }
24+
unsafe { msg_send_id![Self::class(), processInfo].unwrap() }
2625
}
2726

2827
pub fn process_name(&self) -> Id<NSString, Shared> {
29-
let obj: *mut NSString = unsafe { msg_send![Self::class(), processName] };
30-
unsafe { Id::retain_autoreleased(obj).unwrap() }
28+
unsafe { msg_send_id![self, processName].unwrap() }
3129
}
3230
}

objc2-foundation/src/thread.rs

Lines changed: 6 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
use objc2::rc::{Id, Shared};
2-
use objc2::{msg_send, msg_send_bool};
2+
use objc2::{msg_send, msg_send_bool, msg_send_id};
33

44
use crate::{NSObject, NSString};
55

@@ -15,20 +15,18 @@ unsafe impl Sync for NSThread {}
1515

1616
impl NSThread {
1717
/// Returns the [`NSThread`] object representing the current thread.
18-
pub fn current() -> Id<NSThread, Shared> {
18+
pub fn current() -> Id<Self, Shared> {
1919
// TODO: currentThread is @property(strong), what does that mean?
20-
let obj: *mut Self = unsafe { msg_send![Self::class(), currentThread] };
2120
// TODO: Always available?
22-
unsafe { Id::retain_autoreleased(obj).unwrap() }
21+
unsafe { msg_send_id![Self::class(), currentThread].unwrap() }
2322
}
2423

2524
/// Returns the [`NSThread`] object representing the main thread.
2625
pub fn main() -> Id<NSThread, Shared> {
2726
// TODO: mainThread is @property(strong), what does that mean?
28-
let obj: *mut Self = unsafe { msg_send![Self::class(), mainThread] };
2927
// The main thread static may not have been initialized
3028
// This can at least fail in GNUStep!
31-
unsafe { Id::retain_autoreleased(obj).expect("Could not retrieve main thread.") }
29+
unsafe { msg_send_id![Self::class(), mainThread] }.expect("Could not retrieve main thread.")
3230
}
3331

3432
/// Returns `true` if the thread is the main thread.
@@ -38,13 +36,11 @@ impl NSThread {
3836

3937
/// The name of the thread.
4038
pub fn name(&self) -> Option<Id<NSString, Shared>> {
41-
let obj: *mut NSString = unsafe { msg_send![self, name] };
42-
unsafe { Id::retain_autoreleased(obj) }
39+
unsafe { msg_send_id![self, name] }
4340
}
4441

4542
fn new() -> Id<Self, Shared> {
46-
let obj: *mut Self = unsafe { msg_send![Self::class(), new] };
47-
unsafe { Id::new(obj) }.unwrap()
43+
unsafe { msg_send_id![Self::class(), new] }.unwrap()
4844
}
4945

5046
fn start(&self) {

objc2-foundation/src/uuid.rs

Lines changed: 4 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
use objc2::rc::{Id, Shared};
2-
use objc2::{msg_send, Encode, Encoding, RefEncode};
2+
use objc2::{msg_send, msg_send_id, Encode, Encoding, RefEncode};
33

44
use super::{NSCopying, NSObject};
55

@@ -32,19 +32,14 @@ impl NSUUID {
3232
// TODO: `nil` method?
3333

3434
pub fn new_v4() -> Id<Self, Shared> {
35-
unsafe {
36-
let obj: *mut Self = msg_send![Self::class(), alloc];
37-
let obj: *mut Self = msg_send![obj, init];
38-
Id::new(obj).unwrap()
39-
}
35+
unsafe { msg_send_id![Self::class(), new].unwrap() }
4036
}
4137

4238
pub fn from_bytes(bytes: [u8; 16]) -> Id<Self, Shared> {
4339
let bytes = UuidBytes(bytes);
4440
unsafe {
45-
let obj: *mut Self = msg_send![Self::class(), alloc];
46-
let obj: *mut Self = msg_send![obj, initWithUUIDBytes: &bytes];
47-
Id::new(obj).unwrap()
41+
let obj = msg_send_id![Self::class(), alloc];
42+
msg_send_id![obj, initWithUUIDBytes: &bytes].unwrap()
4843
}
4944
}
5045

0 commit comments

Comments
 (0)