Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
Show all changes
31 commits
Select commit Hold shift + click to select a range
6d4f05c
Some awful attempts
EgorkaKulikov Oct 28, 2023
4aa8a10
Initially implemented a converter of UTestInst to UtModel
EgorkaKulikov Oct 30, 2023
ddcf870
Refactor JcToUtModelConverter basing on UTestInst2UtModel converter
EgorkaKulikov Oct 31, 2023
9532b8a
Some steps to implement JcToUtExecutionConverter
EgorkaKulikov Oct 31, 2023
d79ea8b
Implement minimalistic jc to ut execution conversion, enable codegen
IlyaMuravjov Nov 1, 2023
8e30b30
Some improvements
EgorkaKulikov Nov 1, 2023
5935d7b
DeepMapper for models is used
EgorkaKulikov Nov 3, 2023
535abb0
Corrections
EgorkaKulikov Nov 3, 2023
509cb73
Some improvements to JcToUtModelConverter
EgorkaKulikov Nov 3, 2023
21bde03
Further improvements to JcToUtModelConverter
EgorkaKulikov Nov 3, 2023
6471f07
Another converter little improvement
EgorkaKulikov Nov 3, 2023
c14067f
Improve `UtExecutionFailure` creation
IlyaMuravjov Nov 3, 2023
20967a9
Finish implementing `JcToUtModelConverter`
IlyaMuravjov Nov 5, 2023
bf6d497
Refactor nullability in `JcToUtModelConverter` and `JcToUtExecutionCo…
IlyaMuravjov Nov 5, 2023
1a893ad
First version of JC to UT converters without overusing `Descriptor2Va…
IlyaMuravjov Nov 5, 2023
1717235
Processed forgotten call method expression
EgorkaKulikov Nov 7, 2023
f2debe4
Make conversion more class-friendly (do not fail if one method cause …
EgorkaKulikov Nov 7, 2023
c191ed3
Make it possible to use samples in ContestEstimator
EgorkaKulikov Nov 7, 2023
e61cef4
Tested on all primitives
EgorkaKulikov Nov 7, 2023
bb82a6b
contrflow tests added
EgorkaKulikov Nov 7, 2023
13ee51e
More test classes added
EgorkaKulikov Nov 7, 2023
b01d6b3
Add `build/output/test/samples` to `utbot-junit-contest` test projects
IlyaMuravjov Nov 8, 2023
61c1608
Steps to avoid duplicating statements
EgorkaKulikov Nov 8, 2023
f455f99
Merge remote-tracking branch 'origin/egor/jc_to_ut_models_converter' …
EgorkaKulikov Nov 8, 2023
a31d6b1
Make it working correct on IntExamples.max
EgorkaKulikov Nov 8, 2023
98b4398
Remove OptimizeImportsProcessor (seems it was not called, but a sourc…
EgorkaKulikov Nov 8, 2023
0ca848a
Process UTestStaticMethodCall
EgorkaKulikov Nov 8, 2023
9442c72
Comment out includes for IDE related projects in `settings.gradle.kts`
IlyaMuravjov Nov 8, 2023
f37c1eb
Avoid using burningwave to export modules on Java 8
IlyaMuravjov Nov 8, 2023
cea02dd
Fix review comments
EgorkaKulikov Nov 8, 2023
813c2d6
Fix review comments
EgorkaKulikov Nov 9, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Next Next commit
Some awful attempts
  • Loading branch information
EgorkaKulikov authored and IlyaMuravjov committed Nov 3, 2023
commit 6d4f05ccae03c80f63313cd785c8b872d74e3203
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package org.utbot.contest.usvm

import org.jacodb.api.JcType
import org.jacodb.api.TypeName
import org.utbot.framework.plugin.api.ClassId
import org.utbot.framework.plugin.api.util.id
import org.utbot.framework.plugin.api.util.objectClassId

val JcType?.classId: ClassId
get() = this?.javaClass?.id ?: objectClassId

val TypeName.classId: ClassId
get() = ClassId(this.typeName)
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import org.usvm.instrumentation.util.enclosingClass
import org.usvm.instrumentation.util.enclosingMethod
import org.utbot.contest.usvm.executor.JcExecution
import org.utbot.framework.plugin.api.Coverage
import org.utbot.framework.plugin.api.EnvironmentModels
import org.utbot.framework.plugin.api.Instruction
import org.utbot.framework.plugin.api.MissingState
import org.utbot.framework.plugin.api.UtExecution
Expand All @@ -29,51 +30,49 @@ import java.util.*
class JcToUtExecutionConverter(
private val instructionIdProvider: InstructionIdProvider
) {
private val valueConstructor = Descriptor2ValueConverter(utContext.classLoader)

private val utModelConstructor = UtModelConstructor(
objectToModelCache = IdentityHashMap(),
idGenerator = StateBeforeAwareIdGenerator(allPreExistingModels = emptySet()),
utModelWithCompositeOriginConstructorFinder = { classId ->
javaStdLibModelWithCompositeOriginConstructors[classId.jClass]?.invoke()
}
)
private val modelConverter = JcToUtModelConverter()

fun convert(jcExecution: JcExecution): UtExecution? {
// TODO usvm-sbft: convert everything other than coverage
return UtUsvmExecution(
stateBefore = MissingState,
stateAfter = MissingState,
result = UtExecutionSuccess(UtVoidModel),
coverage = convertCoverage(getTrace(jcExecution.uTestExecutionResult), jcExecution.method.enclosingType.jcClass),
instrumentation = emptyList()
)
// val coverage = Coverage(convertCoverage())
// return when (jcExecution.uTestExecutionResult) {
// is UTestExecutionSuccessResult -> {
//
// TODO("usvm-sbft")
// }
// is UTestExecutionExceptionResult -> TODO("usvm-sbft")
// is UTestExecutionInitFailedResult -> {
// val exception =
// valueConstructor.buildObjectFromDescriptor(jcExecution.uTestExecutionResult.cause) as Throwable
// logger.error(exception) { "Concrete executor failed" }
// null
// }
// is UTestExecutionFailedResult -> {
// val exception =
// valueConstructor.buildObjectFromDescriptor(jcExecution.uTestExecutionResult.cause) as Throwable
// if (!jcExecution.uTestExecutionResult.cause.raisedByUserCode)
// logger.error(exception) { "Concrete executor failed" }
// // TODO usvm-sbft
// null
// }
// is UTestExecutionTimedOutResult -> {
// // TODO usvm-sbft
// null
// }
// }
val coverage = convertCoverage(getTrace(jcExecution.uTestExecutionResult), jcExecution.method.enclosingType.jcClass)

val executionResult = jcExecution.uTestExecutionResult
return when (executionResult) {
is UTestExecutionSuccessResult -> {
val result = UtExecutionSuccess(modelConverter.convert(executionResult.result))

UtUsvmExecution(
stateBefore = MissingState,
stateAfter = MissingState,
result = result,
coverage = coverage,
instrumentation = emptyList()
)
}

is UTestExecutionExceptionResult -> TODO("usvm-sbft")
is UTestExecutionInitFailedResult -> {
val exception =
valueConstructor.buildObjectFromDescriptor(jcExecution.uTestExecutionResult.cause) as Throwable
logger.error(exception) { "Concrete executor failed" }
null
}

is UTestExecutionFailedResult -> {
val exception =
valueConstructor.buildObjectFromDescriptor(jcExecution.uTestExecutionResult.cause) as Throwable
if (!jcExecution.uTestExecutionResult.cause.raisedByUserCode)
logger.error(exception) { "Concrete executor failed" }
// TODO usvm-sbft
null
}

is UTestExecutionTimedOutResult -> {
// TODO usvm-sbft
null
}
}

}

private fun getTrace(executionResult: UTestExecutionResult): List<JcInst>? = when (executionResult) {
Expand All @@ -86,13 +85,13 @@ class JcToUtExecutionConverter(

private fun convertCoverage(jcCoverage: List<JcInst>?, jcClass: JcClassOrInterface) = Coverage(
coveredInstructions = jcCoverage.orEmpty().map {
val methodSignature = it.enclosingMethod.jcdbSignature
Instruction(
internalName = it.enclosingClass.name.replace('.', '/'),
methodSignature = methodSignature,
lineNumber = it.lineNumber,
id = instructionIdProvider.provideInstructionId(methodSignature, it.location.index)
)
val methodSignature = it.enclosingMethod.jcdbSignature
Instruction(
internalName = it.enclosingClass.name.replace('.', '/'),
methodSignature = methodSignature,
lineNumber = it.lineNumber,
id = instructionIdProvider.provideInstructionId(methodSignature, it.location.index)
)
},
// TODO usvm-sbft: maybe add cache here
// TODO usvm-sbft: make sure static initializers are included into instructions count
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,131 @@
package org.utbot.contest.usvm

import org.jacodb.analysis.library.analyzers.thisInstance
import org.usvm.instrumentation.classloader.WorkerClassLoader
import org.usvm.instrumentation.testcase.api.UTestExpression
import org.usvm.instrumentation.testcase.api.UTestMock
import org.usvm.instrumentation.testcase.api.UTestMockObject
import org.usvm.instrumentation.testcase.descriptor.Descriptor2ValueConverter
import org.usvm.instrumentation.testcase.descriptor.UTestValueDescriptor
import org.usvm.instrumentation.testcase.descriptor.Value2DescriptorConverter
import org.usvm.instrumentation.testcase.executor.UTestExpressionExecutor
import org.usvm.instrumentation.util.toJavaClass
import org.usvm.instrumentation.util.toJavaField
import org.utbot.framework.plugin.api.ExecutableId
import org.utbot.framework.plugin.api.FieldId
import org.utbot.framework.plugin.api.MethodId
import org.utbot.framework.plugin.api.UtCompositeModel
import org.utbot.framework.plugin.api.UtModel
import org.utbot.framework.plugin.api.UtNullModel
import org.utbot.framework.plugin.api.util.fieldId
import org.utbot.framework.plugin.api.util.id
import org.utbot.framework.plugin.api.util.jClass
import org.utbot.framework.plugin.api.util.objectClassId
import org.utbot.framework.plugin.api.util.utContext
import org.utbot.instrumentation.instrumentation.execution.constructors.StateBeforeAwareIdGenerator
import org.utbot.instrumentation.instrumentation.execution.constructors.UtModelConstructor
import org.utbot.instrumentation.instrumentation.execution.constructors.javaStdLibModelWithCompositeOriginConstructors
import java.util.*

class JcToUtModelConverter {

private val classLoader = utContext.classLoader
private val toValueConverter = Descriptor2ValueConverter(classLoader)

// TODO: properly deal with test executor and related features
private val testExecutor = UTestExpressionExecutor()
private val toDescriptorConverter = Value2DescriptorConverter(WorkerClassLoader(), null)


private val utModelConstructor = UtModelConstructor(
objectToModelCache = IdentityHashMap(),
idGenerator = StateBeforeAwareIdGenerator(allPreExistingModels = emptySet()),
utModelWithCompositeOriginConstructorFinder = { classId ->
javaStdLibModelWithCompositeOriginConstructors[classId.jClass]?.invoke()
}
)

private val exprToModelCache = mutableMapOf<UTestMock, UtCompositeModel>()
private val descrToModelCache = mutableMapOf<UTestValueDescriptor, UtModel>()

fun convert(valueDescriptor: UTestValueDescriptor?): UtModel {
//WTF, how can it happen? but null can be passed here
if (valueDescriptor == null) {
return UtNullModel(objectClassId)
}

return descrToModelCache.getOrPut(valueDescriptor) {
val concreteValue = toValueConverter.buildObjectFromDescriptor(valueDescriptor)
val objectType = valueDescriptor.type.toJavaClass(classLoader).id

val mocklessModel = utModelConstructor.construct(concreteValue, objectType)

if (mocklessModel !is UtCompositeModel) {
return mocklessModel
}

val instantiatingExpr: UTestMock = // TODO: valueDescriptor.instantiatingExpr
UTestMockObject(valueDescriptor.type, emptyMap(), emptyMap())

restoreMockInfo(instantiatingExpr, mocklessModel)
}
}


private fun restoreMockInfo(
mockExpr: UTestMock,
mocklessModel: UtCompositeModel,
): UtModel {

exprToModelCache[mockExpr]?.let { return it }

val fields = mutableMapOf<FieldId, UtModel>()
val mocks = mutableMapOf<ExecutableId, List<UtModel>>()

val finalModel = UtCompositeModel(
id = mocklessModel.id,
classId = mocklessModel.classId,
isMock = true,
fields = fields,
mocks = mocks,
)
exprToModelCache[mockExpr] = finalModel

fields += mockExpr.fields
.entries
.associate { (jcField, uTestExpr) ->
val fieldType = jcField.toJavaField(classLoader)!!.fieldId.type
val fieldId = FieldId(fieldType, jcField.name)

val fieldModelDescr = exprToDescriptor(uTestExpr)

val fieldModel = convert(fieldModelDescr)
fieldId to fieldModel
}
.toMutableMap()

mocks += mockExpr.methods
.entries
.associate { (jcMethod, uTestExprs) ->
val type = jcMethod.thisInstance.type.classId
val returnType = jcMethod.returnType.classId
val parameters = jcMethod.parameters.map { it.type.classId }
val executableId: ExecutableId = MethodId(type, jcMethod.name, returnType, parameters)

val models = uTestExprs
.map { expr -> exprToDescriptor(expr) }
.map { descr -> convert(descr) }

executableId to models
}
.toMutableMap()

return finalModel
}

private fun exprToDescriptor(expr: UTestExpression): UTestValueDescriptor =
toDescriptorConverter
.buildDescriptorFromUTestExpr(expr, testExecutor)
?.getOrNull()!!
.valueDescriptor!!
}