translator: fields generation, parsing var(val) type reference
This commit is contained in:
@@ -1,5 +1,6 @@
|
|||||||
package org.kotlinnative.translator
|
package org.kotlinnative.translator
|
||||||
|
|
||||||
|
import org.jetbrains.kotlin.descriptors.ClassDescriptor
|
||||||
import org.jetbrains.kotlin.descriptors.ClassKind
|
import org.jetbrains.kotlin.descriptors.ClassKind
|
||||||
import org.jetbrains.kotlin.psi.KtClass
|
import org.jetbrains.kotlin.psi.KtClass
|
||||||
import org.jetbrains.kotlin.psi.KtNamedFunction
|
import org.jetbrains.kotlin.psi.KtNamedFunction
|
||||||
@@ -13,7 +14,6 @@ import java.util.*
|
|||||||
class ClassCodegen(val state: TranslationState, val variableManager: VariableManager, val clazz: KtClass, val codeBuilder: LLVMBuilder) {
|
class ClassCodegen(val state: TranslationState, val variableManager: VariableManager, val clazz: KtClass, val codeBuilder: LLVMBuilder) {
|
||||||
|
|
||||||
val annotation: Boolean
|
val annotation: Boolean
|
||||||
val plain: Boolean = false // TODO
|
|
||||||
val fields = ArrayList<LLVMVariable>()
|
val fields = ArrayList<LLVMVariable>()
|
||||||
val fieldsIndex = HashMap<String, LLVMClassVariable>()
|
val fieldsIndex = HashMap<String, LLVMClassVariable>()
|
||||||
val type: LLVMType = LLVMReferenceType(clazz.name.toString(), "class", byRef = true)
|
val type: LLVMType = LLVMReferenceType(clazz.name.toString(), "class", byRef = true)
|
||||||
@@ -24,22 +24,29 @@ class ClassCodegen(val state: TranslationState, val variableManager: VariableMan
|
|||||||
val descriptor = state.bindingContext.get(BindingContext.CLASS, clazz) ?: throw TranslationException()
|
val descriptor = state.bindingContext.get(BindingContext.CLASS, clazz) ?: throw TranslationException()
|
||||||
val parameterList = clazz.getPrimaryConstructorParameterList()?.parameters ?: listOf()
|
val parameterList = clazz.getPrimaryConstructorParameterList()?.parameters ?: listOf()
|
||||||
|
|
||||||
|
annotation = descriptor.kind == ClassKind.ANNOTATION_CLASS
|
||||||
|
size = indexFields(descriptor, parameterList)
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun indexFields(descriptor: ClassDescriptor, parameters: MutableList<KtParameter>): Int {
|
||||||
|
if (annotation) {
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
|
||||||
var offset = 0
|
var offset = 0
|
||||||
var currentSize = 0
|
var currentSize = 0
|
||||||
annotation = descriptor.kind == ClassKind.ANNOTATION_CLASS
|
|
||||||
|
|
||||||
if (!annotation) {
|
for (field in parameters) {
|
||||||
for (field in parameterList) {
|
val item = resolveType(field)
|
||||||
val item = resolveType(field)
|
item.offset = offset
|
||||||
item.offset = offset
|
|
||||||
|
|
||||||
fields.add(item)
|
fields.add(item)
|
||||||
fieldsIndex[item.label] = item
|
fieldsIndex[item.label] = item
|
||||||
|
|
||||||
currentSize += type.size
|
currentSize += type.size
|
||||||
offset++
|
offset++
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
when (descriptor.kind) {
|
when (descriptor.kind) {
|
||||||
ClassKind.ENUM_CLASS -> {
|
ClassKind.ENUM_CLASS -> {
|
||||||
val item = LLVMClassVariable("enum_item", LLVMEnumItemType())
|
val item = LLVMClassVariable("enum_item", LLVMEnumItemType())
|
||||||
@@ -51,7 +58,7 @@ class ClassCodegen(val state: TranslationState, val variableManager: VariableMan
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
size = currentSize
|
return currentSize
|
||||||
}
|
}
|
||||||
|
|
||||||
fun generate() {
|
fun generate() {
|
||||||
|
|||||||
@@ -124,7 +124,7 @@ class FunctionCodegen(val state: TranslationState, val variableManager: Variable
|
|||||||
private fun expressionWalker(expr: PsiElement?, scopeDepth: Int) {
|
private fun expressionWalker(expr: PsiElement?, scopeDepth: Int) {
|
||||||
when (expr) {
|
when (expr) {
|
||||||
is KtBlockExpression -> expressionWalker(expr.firstChild, scopeDepth + 1)
|
is KtBlockExpression -> expressionWalker(expr.firstChild, scopeDepth + 1)
|
||||||
is KtProperty -> evaluateLeafPsiElement(expr.firstChild as LeafPsiElement, scopeDepth)
|
is KtProperty -> evaluateValExpression(expr, scopeDepth)
|
||||||
is KtBinaryExpression -> evaluateBinaryExpression(expr, scopeDepth)
|
is KtBinaryExpression -> evaluateBinaryExpression(expr, scopeDepth)
|
||||||
is KtCallExpression -> evaluateCallExpression(expr, scopeDepth)
|
is KtCallExpression -> evaluateCallExpression(expr, scopeDepth)
|
||||||
is KtDoWhileExpression -> evaluateDoWhileExpression(expr.firstChild, scopeDepth + 1)
|
is KtDoWhileExpression -> evaluateDoWhileExpression(expr.firstChild, scopeDepth + 1)
|
||||||
@@ -348,20 +348,25 @@ class FunctionCodegen(val state: TranslationState, val variableManager: Variable
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun evaluateTypeReference(element: KtTypeReference): LLVMSingleValue? {
|
private fun evaluateTypeReference(element: KtTypeReference): LLVMSingleValue? {
|
||||||
val type = element.typeElement as KtUserType
|
val type = element.typeElement
|
||||||
val operator = element.getNextSiblingIgnoringWhitespaceAndComments()
|
val operator = element.getNextSiblingIgnoringWhitespaceAndComments()
|
||||||
val value = operator?.getNextSiblingIgnoringWhitespaceAndComments() as KtConstantExpression
|
val value = operator?.getNextSiblingIgnoringWhitespaceAndComments() as KtConstantExpression
|
||||||
|
|
||||||
return when (operator) {
|
when (type) {
|
||||||
else -> throw UnsupportedOperationException()
|
is KtUserType -> {
|
||||||
|
val i = 1
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// return when (operator) {
|
||||||
|
// else -> throw UnsupportedOperationException()
|
||||||
|
// }
|
||||||
|
return null
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun evaluateLeafPsiElement(element: LeafPsiElement, scopeDepth: Int): LLVMVariable? {
|
private fun evaluateLeafPsiElement(element: LeafPsiElement, scopeDepth: Int): LLVMVariable? {
|
||||||
return when (element.elementType) {
|
return when (element.elementType) {
|
||||||
KtTokens.RETURN_KEYWORD -> evaluateReturnInstruction(element, scopeDepth)
|
KtTokens.RETURN_KEYWORD -> evaluateReturnInstruction(element, scopeDepth)
|
||||||
KtTokens.VAL_KEYWORD -> evaluateValExpression(element, scopeDepth)
|
|
||||||
KtTokens.VAR_KEYWORD -> evaluateValExpression(element, scopeDepth)
|
|
||||||
KtTokens.IF_KEYWORD -> evaluateIfOperator(element, scopeDepth, containReturn = false)
|
KtTokens.IF_KEYWORD -> evaluateIfOperator(element, scopeDepth, containReturn = false)
|
||||||
KtTokens.WHILE_KEYWORD -> evaluateWhileOperator(element, scopeDepth)
|
KtTokens.WHILE_KEYWORD -> evaluateWhileOperator(element, scopeDepth)
|
||||||
else -> null
|
else -> null
|
||||||
@@ -450,29 +455,29 @@ class FunctionCodegen(val state: TranslationState, val variableManager: Variable
|
|||||||
else -> codeBuilder.copyVariableValue(to, from)
|
else -> codeBuilder.copyVariableValue(to, from)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun evaluateValExpression(element: LeafPsiElement, scopeDepth: Int): LLVMVariable? {
|
private fun evaluateValExpression(element: KtProperty, scopeDepth: Int): LLVMVariable? {
|
||||||
val identifier = element.getNextSiblingIgnoringWhitespaceAndComments()
|
val variable = state.bindingContext.get(BindingContext.VARIABLE, element)!!
|
||||||
val eq = identifier?.getNextSiblingIgnoringWhitespaceAndComments() ?: return null
|
val identifier = variable.name.toString()
|
||||||
|
|
||||||
val assignExpression = evaluateExpression(eq.getNextSiblingIgnoringWhitespaceAndComments(), scopeDepth) ?: return null
|
val assignExpression = evaluateExpression(element.delegateExpressionOrInitializer, scopeDepth) ?: return null
|
||||||
|
|
||||||
when (assignExpression) {
|
when (assignExpression) {
|
||||||
is LLVMVariable -> {
|
is LLVMVariable -> {
|
||||||
if (assignExpression.pointer == 0) {
|
if (assignExpression.pointer == 0) {
|
||||||
val allocVar = variableManager.receiveVariable(identifier!!.text, assignExpression.type, LLVMRegisterScope(), pointer = 0)
|
val allocVar = variableManager.receiveVariable(identifier, assignExpression.type, LLVMRegisterScope(), pointer = 0)
|
||||||
codeBuilder.allocStackVar(allocVar)
|
codeBuilder.allocStackVar(allocVar)
|
||||||
allocVar.pointer++
|
allocVar.pointer++
|
||||||
variableManager.addVariable(identifier.text, allocVar, scopeDepth)
|
variableManager.addVariable(identifier, allocVar, scopeDepth)
|
||||||
copyVariable(assignExpression, allocVar)
|
copyVariable(assignExpression, allocVar)
|
||||||
} else {
|
} else {
|
||||||
variableManager.addVariable(identifier!!.text, assignExpression, scopeDepth)
|
variableManager.addVariable(identifier, assignExpression, scopeDepth)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
is LLVMConstant -> {
|
is LLVMConstant -> {
|
||||||
val newVar = variableManager.receiveVariable(identifier!!.text, assignExpression.type!!, LLVMRegisterScope(), pointer = 1)
|
val newVar = variableManager.receiveVariable(identifier, assignExpression.type!!, LLVMRegisterScope(), pointer = 1)
|
||||||
|
|
||||||
codeBuilder.addConstant(newVar, assignExpression)
|
codeBuilder.addConstant(newVar, assignExpression)
|
||||||
variableManager.addVariable(identifier.text, newVar, scopeDepth)
|
variableManager.addVariable(identifier, newVar, scopeDepth)
|
||||||
}
|
}
|
||||||
else -> {
|
else -> {
|
||||||
throw UnsupportedOperationException()
|
throw UnsupportedOperationException()
|
||||||
|
|||||||
Reference in New Issue
Block a user