Optional constructor
This commit is contained in:
@@ -12,7 +12,7 @@ pub struct ClassProcessedData {
|
|||||||
self_path: ExprPath,
|
self_path: ExprPath,
|
||||||
self_ty: TypeExpr,
|
self_ty: TypeExpr,
|
||||||
fields: Vec<Spanned<FieldDeclStmt>>,
|
fields: Vec<Spanned<FieldDeclStmt>>,
|
||||||
constructor: Spanned<ClassConstructor>,
|
constructor: Option<Spanned<ClassConstructor>>,
|
||||||
items: Vec<ClassItem>,
|
items: Vec<ClassItem>,
|
||||||
methods: Vec<Spanned<FunctionDecl>>,
|
methods: Vec<Spanned<FunctionDecl>>,
|
||||||
v_table: Vec<Identifier>,
|
v_table: Vec<Identifier>,
|
||||||
@@ -26,7 +26,7 @@ impl ClassProcessedData {
|
|||||||
generics: &GenericsDecl,
|
generics: &GenericsDecl,
|
||||||
inherits: &Option<ExprPath>,
|
inherits: &Option<ExprPath>,
|
||||||
fields: &Vec<Spanned<FieldDeclStmt>>,
|
fields: &Vec<Spanned<FieldDeclStmt>>,
|
||||||
constructor: &Spanned<ClassConstructor>,
|
constructor: &Option<Spanned<ClassConstructor>>,
|
||||||
items: &Vec<ClassItem>,
|
items: &Vec<ClassItem>,
|
||||||
) -> Self {
|
) -> Self {
|
||||||
let self_path = ExprPath(vec![ExprPathSegment {
|
let self_path = ExprPath(vec![ExprPathSegment {
|
||||||
@@ -136,7 +136,9 @@ impl ClassProcessedData {
|
|||||||
self.emit_unified_vtable(cg);
|
self.emit_unified_vtable(cg);
|
||||||
self.emit_super_v_tests(cg);
|
self.emit_super_v_tests(cg);
|
||||||
|
|
||||||
self.emit_constructor(ctx, cg);
|
if let Some(constructor) = &self.constructor {
|
||||||
|
self.emit_constructor(constructor, ctx, cg);
|
||||||
|
}
|
||||||
self.emit_methods(ctx, cg);
|
self.emit_methods(ctx, cg);
|
||||||
|
|
||||||
cg.indent -= 1;
|
cg.indent -= 1;
|
||||||
@@ -295,7 +297,7 @@ impl ClassProcessedData {
|
|||||||
|
|
||||||
// Deref tests for override targets
|
// Deref tests for override targets
|
||||||
if self.inherits.is_some() && !self.override_v_table.is_empty() {
|
if self.inherits.is_some() && !self.override_v_table.is_empty() {
|
||||||
cg.add_indentedln("let this: &Self = &unsafe { std::mem::MaybeUninit::<Self>::zeroed().assume_init() };");
|
cg.add_indentedln("let this: &Self = &unsafe { std::mem::MaybeUninit::<Self>::zeroed().assume_init() };");
|
||||||
|
|
||||||
for (override_tier, v) in &self.override_v_table {
|
for (override_tier, v) in &self.override_v_table {
|
||||||
if let Some(path) = &override_tier.0 {
|
if let Some(path) = &override_tier.0 {
|
||||||
@@ -310,20 +312,24 @@ impl ClassProcessedData {
|
|||||||
cg.add_indentedln("}");
|
cg.add_indentedln("}");
|
||||||
}
|
}
|
||||||
|
|
||||||
fn emit_constructor(&self, ctx: &mut Context, cg: &mut RustCodegen) {
|
fn emit_constructor(
|
||||||
let constructor_comment = self.constructor.get_comment();
|
&self,
|
||||||
|
constructor: &Spanned<ClassConstructor>,
|
||||||
|
ctx: &mut Context,
|
||||||
|
cg: &mut RustCodegen,
|
||||||
|
) {
|
||||||
|
let constructor_comment = constructor.get_comment();
|
||||||
|
|
||||||
cg.add_indentedln("#[allow(invalid_value)]");
|
cg.add_indentedln("#[allow(invalid_value)]");
|
||||||
cg.add_indentedln(&constructor_comment);
|
cg.add_indentedln(&constructor_comment);
|
||||||
|
|
||||||
cg.add_indented(&format!(
|
cg.add_indented(&format!(
|
||||||
"{}fn new{}(",
|
"{}fn new{}(",
|
||||||
self.constructor.item.visibility.get_rust(),
|
constructor.item.visibility.get_rust(),
|
||||||
self.constructor.item.generics.get_rust()
|
constructor.item.generics.get_rust()
|
||||||
));
|
));
|
||||||
|
|
||||||
let params = self
|
let params = constructor
|
||||||
.constructor
|
|
||||||
.item
|
.item
|
||||||
.params
|
.params
|
||||||
.0
|
.0
|
||||||
@@ -389,19 +395,19 @@ impl ClassProcessedData {
|
|||||||
}),
|
}),
|
||||||
}];
|
}];
|
||||||
|
|
||||||
constructor_params.append(&mut self.constructor.item.params.0.clone());
|
constructor_params.append(&mut constructor.item.params.0.clone());
|
||||||
|
|
||||||
Spanned {
|
Spanned {
|
||||||
line: self.constructor.line,
|
line: constructor.line,
|
||||||
column: self.constructor.column,
|
column: constructor.column,
|
||||||
item: FunctionDecl {
|
item: FunctionDecl {
|
||||||
visibility: self.constructor.item.visibility.clone(),
|
visibility: constructor.item.visibility.clone(),
|
||||||
is_override: None,
|
is_override: None,
|
||||||
name: Identifier(String::from("constructor")),
|
name: Identifier(String::from("constructor")),
|
||||||
generics: self.constructor.item.generics.clone(),
|
generics: constructor.item.generics.clone(),
|
||||||
params: ParamList(constructor_params),
|
params: ParamList(constructor_params),
|
||||||
return_type: Some(TypeExpr::Tuple(Vec::new())),
|
return_type: Some(TypeExpr::Tuple(Vec::new())),
|
||||||
body: Some(self.constructor.item.body.clone()),
|
body: Some(constructor.item.body.clone()),
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
.gen_rust(ctx, cg);
|
.gen_rust(ctx, cg);
|
||||||
@@ -491,7 +497,7 @@ pub fn class_decl(
|
|||||||
generics: &GenericsDecl,
|
generics: &GenericsDecl,
|
||||||
inherits: &Option<ExprPath>,
|
inherits: &Option<ExprPath>,
|
||||||
fields: &Vec<Spanned<FieldDeclStmt>>,
|
fields: &Vec<Spanned<FieldDeclStmt>>,
|
||||||
constructor: &Spanned<ClassConstructor>,
|
constructor: &Option<Spanned<ClassConstructor>>,
|
||||||
items: &Vec<ClassItem>,
|
items: &Vec<ClassItem>,
|
||||||
) {
|
) {
|
||||||
let data = ClassProcessedData::analyze(
|
let data = ClassProcessedData::analyze(
|
||||||
|
|||||||
@@ -56,7 +56,7 @@ pub enum TopLevelKind {
|
|||||||
generics: GenericsDecl,
|
generics: GenericsDecl,
|
||||||
inherits: Option<ExprPath>,
|
inherits: Option<ExprPath>,
|
||||||
fields: Vec<Spanned<FieldDeclStmt>>,
|
fields: Vec<Spanned<FieldDeclStmt>>,
|
||||||
constructor: Spanned<ClassConstructor>,
|
constructor: Option<Spanned<ClassConstructor>>,
|
||||||
items: Vec<ClassItem>,
|
items: Vec<ClassItem>,
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -292,7 +292,7 @@ class_item = _{
|
|||||||
}
|
}
|
||||||
|
|
||||||
class_decl = {
|
class_decl = {
|
||||||
visibility? ~ "class" ~ identifier ~ generics_decl? ~ (":" ~ expr_path)? ~ "{" ~ class_fields ~ class_constructor ~ class_item* ~ "}"
|
visibility? ~ "class" ~ identifier ~ generics_decl? ~ (":" ~ expr_path)? ~ "{" ~ class_fields ~ class_constructor? ~ class_item* ~ "}"
|
||||||
}
|
}
|
||||||
|
|
||||||
// ======================================================
|
// ======================================================
|
||||||
|
|||||||
@@ -75,7 +75,9 @@ impl<'a> TryFrom<pest::iterators::Pair<'a, Rule>> for TopLevelKind {
|
|||||||
|
|
||||||
fields: collect_recovered(inner.next().unwrap().into_inner()),
|
fields: collect_recovered(inner.next().unwrap().into_inner()),
|
||||||
|
|
||||||
constructor: inner.next().unwrap().try_into(),
|
constructor: consume_rule(&mut inner, Rule::class_constructor)
|
||||||
|
.map(Spanned::try_from)
|
||||||
|
.transpose(),
|
||||||
|
|
||||||
items: collect_recovered(inner),
|
items: collect_recovered(inner),
|
||||||
}),
|
}),
|
||||||
|
|||||||
Reference in New Issue
Block a user