Skip to content

Commit

Permalink
std/comptime: add the FieldByIndex method to comptimeValue
Browse files Browse the repository at this point in the history
  • Loading branch information
mertcandav committed Nov 11, 2024
1 parent 354195e commit 9dba214
Show file tree
Hide file tree
Showing 3 changed files with 47 additions and 0 deletions.
3 changes: 3 additions & 0 deletions std/comptime/value.jule
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,9 @@ impl comptimeValue {
// It allows access to private fields.
fn Field(self, ident: str): comptimeValue

// Same as the Field method, but takes constant index istead of identifier.
fn FieldByIndex(self, index: int): comptimeValue

// Returns comptimeValue for method access expression.
// Supports only structure types.
// Parameter ident should be constant.
Expand Down
1 change: 1 addition & 0 deletions std/jule/build/log.jule
Original file line number Diff line number Diff line change
Expand Up @@ -250,6 +250,7 @@ enum LogMsg: str {
InvalidImportPath: `invalid import path: @`,
AutoAliasFail: `import path is not suitable for auto-aliasing: @`,
BindedAsSoftType: `binded type aliases cannot be soft type alias`,
IndexOutOfRange: `index @ out of range of length @`,

// Suggestions.
ExpectedIdentifier: `write an identifier because identifier expected`,
Expand Down
43 changes: 43 additions & 0 deletions std/jule/sema/comptime.jule
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD 3-Clause
// license that can be found in the LICENSE file.

use "std/conv"
use "std/jule/ast"
use "std/jule/build"
use "std/jule/constant"
Expand Down Expand Up @@ -1230,6 +1231,41 @@ impl comptimeValue {
ret buildComptimeValue(d)
}

fn _FieldByIndex(mut &self, mut &e: &eval, mut &fc: &ast::FnCallExpr): &Data {
if len(fc.Args) > 1 {
e.pushErr(fc.Args[1].Token, build::LogMsg.ArgumentOverflow, "FieldByIndex")
ret nil
}
mut s := self.data.Type.Struct()
if s == nil {
e.pushErr(fc.Token, build::LogMsg.InvalidTypeForFn, self.data.Type.Str(), "Field")
ret nil
}
mut arg := fc.Args[0]
mut d := e.evalExpr(arg)
if d == nil {
ret nil
}
if !d.IsConst() {
e.pushErr(arg.Token, build::LogMsg.ExprNotConst)
ret nil
}
log := checkDataForIntegerIndexing(e.s, d, arg.Token,e.getOwnerRefers())
if log != build::LogMsg.Empty {
e.pushErr(arg.Token, log)
ret nil
}
i := d.Constant.AsU64()
if i >= u64(len(s.Fields)) {
e.pushErr(arg.Token, build::LogMsg.IndexOutOfRange, conv::FmtUint(i, 10), conv::Itoa(len(s.Fields)))
ret nil
}
mut f := s.Fields[i]
d = new(Data, *self.data)
d = e.evalStructSubIdentField(d, s, arg.Token, f)
ret buildComptimeValue(d)
}

fn _Method(mut &self, mut &e: &eval, mut &fc: &ast::FnCallExpr): &Data {
if len(fc.Args) > 1 {
e.pushErr(fc.Args[1].Token, build::LogMsg.ArgumentOverflow, "Method")
Expand Down Expand Up @@ -1321,6 +1357,13 @@ impl comptimeValue {
},
}
ret buildAsComptimeMethodData(method)
| "FieldByIndex":
mut method := &FnIns{
caller: fn(mut &e: &eval, mut &fc: &ast::FnCallExpr, mut &_: &Data): &Data {
ret self._FieldByIndex(e, fc)
},
}
ret buildAsComptimeMethodData(method)
| "Method":
mut method := &FnIns{
caller: fn(mut &e: &eval, mut &fc: &ast::FnCallExpr, mut &_: &Data): &Data {
Expand Down

0 comments on commit 9dba214

Please sign in to comment.