Added untested type mismatch error reporting thing
This commit is contained in:
parent
020833c4c6
commit
41724a7e03
@ -15,6 +15,7 @@ type Argument interface {
|
||||
// FloatLiteral
|
||||
// StringLiteral
|
||||
|
||||
What () (what Type)
|
||||
ToString (indent int) (output string)
|
||||
canBePassedAs (what Type) (allowed bool)
|
||||
}
|
||||
|
8
analyzer/common-errors.go
Normal file
8
analyzer/common-errors.go
Normal file
@ -0,0 +1,8 @@
|
||||
package analyzer
|
||||
|
||||
func typeMismatchErrorMessage (source Type, destination Type) (message string) {
|
||||
message += source.Describe()
|
||||
message += " cannot be used as "
|
||||
message += destination.Describe()
|
||||
return
|
||||
}
|
@ -14,6 +14,13 @@ func (literal IntLiteral) ToString (indent int) (output string) {
|
||||
return
|
||||
}
|
||||
|
||||
// What returns the type of the argument
|
||||
func (literal IntLiteral) What () (what Type) {
|
||||
what.actual = &PrimitiveI64
|
||||
what.length = 1
|
||||
return
|
||||
}
|
||||
|
||||
// canBePassedAs returns true if this literal can be implicitly cast to the
|
||||
// specified type, and false if it can't.
|
||||
func (literal IntLiteral) canBePassedAs (what Type) (allowed bool) {
|
||||
@ -43,6 +50,13 @@ func (literal UIntLiteral) ToString (indent int) (output string) {
|
||||
return
|
||||
}
|
||||
|
||||
// What returns the type of the argument
|
||||
func (literal UIntLiteral) What () (what Type) {
|
||||
what.actual = &PrimitiveU64
|
||||
what.length = 1
|
||||
return
|
||||
}
|
||||
|
||||
// canBePassedAs returns true if this literal can be implicitly cast to the
|
||||
// specified type, and false if it can't.
|
||||
func (literal UIntLiteral) canBePassedAs (what Type) (allowed bool) {
|
||||
@ -71,6 +85,13 @@ func (literal UIntLiteral) canBePassedAs (what Type) (allowed bool) {
|
||||
return
|
||||
}
|
||||
|
||||
// What returns the type of the argument
|
||||
func (literal FloatLiteral) What () (what Type) {
|
||||
what.actual = &PrimitiveF64
|
||||
what.length = 1
|
||||
return
|
||||
}
|
||||
|
||||
// ToString outputs the data in the argument as a string.
|
||||
func (literal FloatLiteral) ToString (indent int) (output string) {
|
||||
output += doIndent(indent, fmt.Sprint("arg float ", literal, "\n"))
|
||||
@ -95,6 +116,13 @@ func (literal FloatLiteral) canBePassedAs (what Type) (allowed bool) {
|
||||
return
|
||||
}
|
||||
|
||||
// What returns the type of the argument
|
||||
func (literal StringLiteral) What () (what Type) {
|
||||
what.actual = &BuiltInString
|
||||
what.length = 1
|
||||
return
|
||||
}
|
||||
|
||||
// ToString outputs the data in the argument as a string.
|
||||
func (literal StringLiteral) ToString (indent int) (output string) {
|
||||
output += doIndent(indent, fmt.Sprint("arg string \"", literal, "\"\n"))
|
||||
|
@ -80,12 +80,16 @@ func (analyzer AnalysisOperation) analyzeTypeSection () (
|
||||
outputSection.argument,
|
||||
err = analyzer.analyzeArgument(inputSection.Argument())
|
||||
if err != nil { return }
|
||||
if !outputSection.argument.canBePassedAs(outputSection.what) {
|
||||
|
||||
// type check default value
|
||||
if !outputSection.argument.canBePassedAs(outputSection.what) {
|
||||
err = inputSection.Argument().NewError (
|
||||
typeMismatchErrorMessage (
|
||||
outputSection.argument.What(),
|
||||
outputSection.what),
|
||||
infoerr.ErrorKindError)
|
||||
return
|
||||
}
|
||||
// TODO: type check default value. possibly add a method to
|
||||
// Argument that takes in a type and determines whether the
|
||||
// argument can fit to it.
|
||||
}
|
||||
|
||||
// TODO: analyze members
|
||||
|
@ -1,6 +1,7 @@
|
||||
package analyzer
|
||||
|
||||
// import "git.tebibyte.media/arf/arf/types"
|
||||
import "fmt"
|
||||
import "path/filepath"
|
||||
import "git.tebibyte.media/arf/arf/parser"
|
||||
import "git.tebibyte.media/arf/arf/infoerr"
|
||||
|
||||
@ -204,3 +205,63 @@ func (analyzer AnalysisOperation) analyzeType (
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
// Describe provides a human readable description of the type. The value of this
|
||||
// should not be computationally analyzed.
|
||||
func (what Type) Describe () (description string) {
|
||||
if what.kind == TypeKindBasic {
|
||||
actual := what.actual
|
||||
switch actual {
|
||||
case &PrimitiveF32:
|
||||
description += "F32"
|
||||
case &PrimitiveF64:
|
||||
description += "F64"
|
||||
case &PrimitiveFunc:
|
||||
description += "Func"
|
||||
case &PrimitiveFace:
|
||||
description += "Face"
|
||||
case &PrimitiveObj:
|
||||
description += "Obj"
|
||||
case &PrimitiveU64:
|
||||
description += "U64"
|
||||
case &PrimitiveU32:
|
||||
description += "U32"
|
||||
case &PrimitiveU16:
|
||||
description += "U16"
|
||||
case &PrimitiveU8:
|
||||
description += "U8"
|
||||
case &PrimitiveI64:
|
||||
description += "I64"
|
||||
case &PrimitiveI32:
|
||||
description += "I32"
|
||||
case &PrimitiveI16:
|
||||
description += "I16"
|
||||
case &PrimitiveI8:
|
||||
description += "I8"
|
||||
case &PrimitiveUInt:
|
||||
description += "UInt"
|
||||
case &PrimitiveInt:
|
||||
description += "Int"
|
||||
|
||||
case nil:
|
||||
panic("invalid state: Type.actual is nil")
|
||||
|
||||
default:
|
||||
locator := actual.locator()
|
||||
description +=
|
||||
filepath.Base(locator.modulePath) +
|
||||
"." + locator.name
|
||||
return
|
||||
}
|
||||
} else {
|
||||
description += "{"
|
||||
description += what.points.Describe()
|
||||
description += "}"
|
||||
}
|
||||
|
||||
if what.length > 0 {
|
||||
description += fmt.Sprint(":", what.length)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
Reference in New Issue
Block a user