Allow associated functions to take self as owned

This commit is contained in:
Sofia 2025-07-27 18:41:51 +03:00
parent 7c6f1a7f9b
commit 0613fc5c53
4 changed files with 23 additions and 10 deletions

View File

@ -13,16 +13,15 @@ impl Otus {
} }
impl i32 { impl i32 {
fn test(&self) -> u32 { fn test(self) -> u32 {
43 43
} }
} }
fn main() -> u32 { fn main() -> u32 {
let otus = Otus { field: 17 }; let otus = Otus { field: 17 };
let num = 54;
print(from_str("otus: ") + Otus::test(&otus) as u64); print(from_str("otus: ") + Otus::test(&otus) as u64);
print(from_str("i32: ") + i32::test(&num) as u64); print(from_str("i32: ") + i32::test(54) as u64);
return Otus::test(&otus); return Otus::test(&otus);
} }

View File

@ -181,6 +181,7 @@ pub struct FunctionSignature {
#[derive(Debug, Clone)] #[derive(Debug, Clone)]
pub enum SelfKind { pub enum SelfKind {
Owned(TypeKind),
Borrow(TypeKind), Borrow(TypeKind),
MutBorrow(TypeKind), MutBorrow(TypeKind),
None, None,

View File

@ -599,23 +599,34 @@ impl Parse for FunctionParam {
#[derive(Debug)] #[derive(Debug)]
pub struct SelfParam(SelfKind); pub struct SelfParam(SelfKind);
pub enum SelfParamKind {
Owned,
Borrow,
BorrowMut,
}
impl Parse for SelfParam { impl Parse for SelfParam {
fn parse(mut stream: TokenStream) -> Result<Self, Error> { fn parse(mut stream: TokenStream) -> Result<Self, Error> {
stream.expect(Token::Et)?; let kind = if let Some(Token::Et) = stream.peek() {
let mutable = if let Some(Token::MutKeyword) = stream.peek() {
stream.next(); stream.next();
true if let Some(Token::MutKeyword) = stream.peek() {
stream.next();
SelfParamKind::BorrowMut
} else { } else {
false SelfParamKind::Borrow
}
} else {
SelfParamKind::Owned
}; };
let Some(Token::Identifier(name)) = stream.next() else { let Some(Token::Identifier(name)) = stream.next() else {
return Err(stream.expected_err("parameter name")?); return Err(stream.expected_err("parameter name")?);
}; };
if name == "self" { if name == "self" {
match mutable { match kind {
true => Ok(SelfParam(SelfKind::MutBorrow(TypeKind::Unknown))), SelfParamKind::BorrowMut => Ok(SelfParam(SelfKind::MutBorrow(TypeKind::Unknown))),
false => Ok(SelfParam(SelfKind::Borrow(TypeKind::Unknown))), SelfParamKind::Borrow => Ok(SelfParam(SelfKind::Borrow(TypeKind::Unknown))),
SelfParamKind::Owned => Ok(SelfParam(SelfKind::Owned(TypeKind::Unknown))),
} }
} else { } else {
Err(stream.expected_err("self parameter")?) Err(stream.expected_err("self parameter")?)
@ -984,6 +995,7 @@ impl Parse for AssociatedFunctionBlock {
while let Some(Token::FnKeyword) = stream.peek() { while let Some(Token::FnKeyword) = stream.peek() {
let mut fun: FunctionDefinition = stream.parse()?; let mut fun: FunctionDefinition = stream.parse()?;
fun.0.self_kind = match fun.0.self_kind { fun.0.self_kind = match fun.0.self_kind {
SelfKind::Owned(_) => SelfKind::Owned(ty.0.clone()),
SelfKind::Borrow(_) => SelfKind::Borrow(ty.0.clone()), SelfKind::Borrow(_) => SelfKind::Borrow(ty.0.clone()),
SelfKind::MutBorrow(_) => SelfKind::MutBorrow(ty.0.clone()), SelfKind::MutBorrow(_) => SelfKind::MutBorrow(ty.0.clone()),
SelfKind::None => SelfKind::None, SelfKind::None => SelfKind::None,

View File

@ -136,6 +136,7 @@ impl ast::FunctionDefinition {
"self".to_owned(), "self".to_owned(),
mir::TypeKind::Borrow(Box::new(type_kind.into_mir(module_id)), true), mir::TypeKind::Borrow(Box::new(type_kind.into_mir(module_id)), true),
)), )),
ast::SelfKind::Owned(type_kind) => params.push(("self".to_owned(), type_kind.into_mir(module_id))),
ast::SelfKind::None => {} ast::SelfKind::None => {}
} }