Skip to content

Commit

Permalink
Parse and ignore extended encoding type information
Browse files Browse the repository at this point in the history
  • Loading branch information
madsmtm committed Dec 3, 2023
1 parent 4ec5b64 commit 2d47b81
Show file tree
Hide file tree
Showing 3 changed files with 31 additions and 2 deletions.
12 changes: 12 additions & 0 deletions crates/objc2-encode/src/encoding.rs
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,14 @@ pub enum Encoding {
/// A C `char *`. Corresponds to the `"*"` code.
String,
/// An Objective-C object (`id`). Corresponds to the `"@"` code.
///
/// Some compilers may choose to store the name of the class in instance
/// variables and properties as `"@" class_name`, see [Extended Type Info
/// in Objective-C][ext] (note that this does not include generics).
///
/// Such class names are currently ignored by `objc2-encode`.
///
/// [ext]: https://bou.io/ExtendedTypeInfoInObjC.html
Object,
/// An Objective-C block. Corresponds to the `"@" "?"` code.
Block,
Expand Down Expand Up @@ -378,6 +386,10 @@ mod tests {
Encoding::Object;
!Encoding::Block;
"@";
~"@\"AnyClassName\"";
~"@\"\""; // Empty class name
!"@\"MyClassName";
!"@MyClassName\"";
!"@?";
}

Expand Down
20 changes: 18 additions & 2 deletions crates/objc2-encode/src/parse.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ use alloc::string::{String, ToString};
use alloc::vec::Vec;
use core::fmt;

use crate::helper::{ContainerKind, EncodingType, Helper, NestingLevel};
use crate::helper::{ContainerKind, EncodingType, Helper, NestingLevel, Primitive};
use crate::{Encoding, EncodingBox};

/// Check whether a struct or union name is a valid identifier
Expand Down Expand Up @@ -251,7 +251,16 @@ impl Parser<'_> {

pub(crate) fn expect_encoding(&mut self, enc: &Encoding, level: NestingLevel) -> Option<()> {
match enc.helper() {
Helper::Primitive(primitive) => self.expect_str(primitive.to_str()),
Helper::Primitive(primitive) => {
self.expect_str(primitive.to_str())?;

if primitive == Primitive::Object && self.try_peek() == Some(b'"') {
self.advance();
self.consume_while(|b| b != b'"');
self.expect_byte(b'"')?;
}
Some(())
}
Helper::BitField(size, Some((offset, t))) => {
self.expect_byte(b'b')?;
self.expect_u64(*offset)?;
Expand Down Expand Up @@ -388,6 +397,13 @@ impl Parser<'_> {
self.advance();
EncodingBox::Block
}
// Parse class name if present
Some(b'"') => {
self.advance();
self.consume_while(|b| b != b'"');
self.expect_byte(b'"').ok_or(ErrorKind::UnexpectedEnd)?;
EncodingBox::Object
}
_ => EncodingBox::Object,
},
b'#' => EncodingBox::Class,
Expand Down
1 change: 1 addition & 0 deletions crates/objc2/src/runtime/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -917,6 +917,7 @@ impl AnyClass {
Bool::from_raw(res).as_bool()
}

// <https://developer.apple.com/library/archive/documentation/Cocoa/Conceptual/ObjCRuntimeGuide/Articles/ocrtPropertyIntrospection.html>
// fn property(&self, name: &str) -> Option<&Property>;
// fn properties(&self) -> Malloc<[&Property]>;
// unsafe fn replace_method(&self, name: Sel, imp: Imp, types: &str) -> Imp;
Expand Down

0 comments on commit 2d47b81

Please sign in to comment.