Skip to content

Commit

Permalink
Merge branch 'develop' into bugfix/NW23001440/mvr-indicators
Browse files Browse the repository at this point in the history
  • Loading branch information
dom-apuliasoft committed Mar 19, 2024
2 parents 5edf310 + 970c7b0 commit f13df5a
Show file tree
Hide file tree
Showing 7 changed files with 111 additions and 15 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -1719,21 +1719,23 @@ data class ScanStmt(
val left: Expression,
val leftLength: Int?,
val right: Expression,
val startPosition: Int,
val startPosition: Expression?,
val target: AssignableExpression?,
val rightIndicators: WithRightIndicators,
@Derived val dataDefinition: InStatementDataDefinition? = null,
override val position: Position? = null
) : Statement(position), WithRightIndicators by rightIndicators, StatementThatCanDefineData {

override fun execute(interpreter: InterpreterCore) {
val start = startPosition?.let { interpreter.eval(it).asString().value.toInt() } ?: 1

val stringToSearch = interpreter.eval(left).asString().value.substringOfLength(leftLength)
val searchInto = interpreter.eval(right).asString().value.substring(startPosition - 1)
val searchInto = interpreter.eval(right).asString().value.substring(start - 1)
val occurrences = mutableListOf<Value>()
var index = -1
do {
index = searchInto.indexOf(stringToSearch, index + 1)
if (index >= 0) occurrences.add(IntValue((index + startPosition).toLong()))
if (index >= 0) occurrences.add(IntValue((index + start).toLong()))
} while (index >= 0)
if (occurrences.isEmpty()) {
interpreter.setIndicators(this, BooleanValue.FALSE, BooleanValue.FALSE, BooleanValue.FALSE)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1316,20 +1316,30 @@ internal fun CsDELETEContext.toAst(conf: ToAstConfiguration): Statement {

internal fun CsSCANContext.toAst(conf: ToAstConfiguration = ToAstConfiguration()): ScanStmt {
val position = toPosition(conf.considerPosition)

val (compareExpression, compareLength) = this.factor1Context().toIndexedExpression(conf)
val (baseExpression, startPosition) = this.cspec_fixed_standard_parts().factor2.toIndexedExpression(conf)

val factor2 = this.cspec_fixed_standard_parts().factor2

val result = this.cspec_fixed_standard_parts().result
val dataDefinition = this.cspec_fixed_standard_parts().toDataDefinition(result.text, position, conf)

val rightIndicators = cspec_fixed_standard_parts().rightIndicators()
val result = this.cspec_fixed_standard_parts().result.text
val dataDefinition = this.cspec_fixed_standard_parts().toDataDefinition(result, position, conf)
val target = when {
result.isNotBlank() -> this.cspec_fixed_standard_parts()!!.result!!.toAst(conf)
else -> null
}
val target = if (result.text.isNotBlank()) result.toAst(conf) else null

val baseExpression = factor2.factorContent(0).toAst(conf)
val positionExpression =
if (factor2.factorContent().size > 1) {
factor2.factorContent(1).toAst(conf)
} else {
null
}

return ScanStmt(
left = compareExpression,
leftLength = compareLength,
right = baseExpression,
startPosition = startPosition ?: 1,
startPosition = positionExpression,
target = target,
rightIndicators = rightIndicators,
dataDefinition = dataDefinition,
Expand Down Expand Up @@ -1378,8 +1388,6 @@ private fun FactorContext.toIndexedExpression(conf: ToAstConfiguration): Pair<Ex
if (this.text.contains(":")) this.text.toIndexedExpression(toPosition(conf.considerPosition)) else this.content.toAst(conf) to null

private fun String.toIndexedExpression(position: Position?): Pair<Expression, Int?> {
fun String.isLiteral(): Boolean { return (startsWith('\'') && endsWith('\'')) }

val baseStringTokens = this.split(":")
val startPosition =
when (baseStringTokens.size) {
Expand All @@ -1389,7 +1397,10 @@ private fun String.toIndexedExpression(position: Position?): Pair<Expression, In
}
val reference = baseStringTokens[0]
return when {
reference.isLiteral() -> StringLiteral(reference.trim('\''), position)
reference.isStringLiteral() -> StringLiteral(reference.trim('\''), position)
reference.contains('(') && reference.endsWith(")") -> {
annidatedReferenceExpression(this, position)
}
else -> DataRefExpr(ReferenceByName(reference), position)
} to startPosition
}
Expand Down Expand Up @@ -2037,3 +2048,5 @@ private fun <T : AbstractDataDefinition> List<T>.removeUnnecessaryRecordFormat()
dataDef.type is RecordFormatType && this.any { it.type is DataStructureType && it.name.uppercase() == dataDef.name.uppercase() }
}
}

private fun String.isStringLiteral(): Boolean = startsWith('\'') && endsWith('\'')
Original file line number Diff line number Diff line change
@@ -1,3 +1,16 @@
package com.smeup.rpgparser.smeup

open class MULANGT02ConstAndDSpecTest : MULANGTTest()
import org.junit.Test
import kotlin.test.assertEquals

open class MULANGT02ConstAndDSpecTest : MULANGTTest() {
/**
* Data reference - Inline definition
* @see #250
*/
@Test
fun executeT02_A80_P01() {
val expected = listOf("ABCDEFGHIJ12345")
assertEquals(expected, "smeup/T02_A80_P01".outputOf())
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -13,4 +13,24 @@ open class MULANGT10BaseCodopTest : MULANGTTest() {
val expected = listOf("A20_N73(2.272) A20_N70(0) A20_N112(11.11) A20_N110(0) A20_N309(4.889964788)")
assertEquals(expected, "smeup/T10_A20_P52".outputOf(configuration = smeupConfig))
}

/**
* SCAN with array in input
* @see #218
*/
@Test
fun executeT10_A35_P08() {
val expected = listOf<String>("A35_AR1(2)(123&5) IN45(1)")
assertEquals(expected, "smeup/T10_A35_P08".outputOf(configuration = smeupConfig))
}

/**
* SCAN with array in result
* @see #244
*/
@Test
fun executeT10_A35_P10() {
val expected = listOf<String>("A35_AR2(01)(5) A35_AR2(02)(6) A35_AR2(03)(0) IN20(1)")
assertEquals(expected, "smeup/T10_A35_P10".outputOf(configuration = smeupConfig))
}
}
10 changes: 10 additions & 0 deletions rpgJavaInterpreter-core/src/test/resources/smeup/T02_A80_P01.rpgle
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
D A80_A10 S 10
D A80_N50 S 5 0
D £DBG_Str S 50 VARYING

C CLEAR A80_A10 10
C CLEAR A80_N50 5 0
C EVAL A80_A10 = 'ABCDEFGHIJ'
C EVAL A80_N50 = 12345
C EVAL £DBG_Str=%TRIM(A80_A10)+%CHAR(A80_N50)
C £DBG_Str DSPLY
18 changes: 18 additions & 0 deletions rpgJavaInterpreter-core/src/test/resources/smeup/T10_A35_P08.rpgle
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
D £DBG_Str S 150 VARYING
D A35_AR1 S 70 DIM(10)
D A35_A1 S 6
D A35_A2 S 1
D A35_AR2 S 2 0 DIM(5)
D $A S 1 0
D I S 2 0

C EVAL A35_AR1(1)='ABCDEF'
C EVAL A35_AR1(2)='123&5'
C EVAL A35_AR1(3)='TEST&'
C EVAL I = 2
C '&' SCAN A35_AR1(I):1 45
C EVAL £DBG_Str=
C 'A35_AR1(2)('+%TRIMR(A35_AR1(2))+') '
C +'IN45('+%CHAR(*IN45)+')'

C £DBG_Str DSPLY
20 changes: 20 additions & 0 deletions rpgJavaInterpreter-core/src/test/resources/smeup/T10_A35_P10.rpgle
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
D £DBG_Str S 150 VARYING
D A35_AR1 S 70 DIM(10)
D A35_A1 S 6
D A35_A2 S 1
D A35_AR2 S 2 0 DIM(5)
D $A S 1 0
D I S 2 0

C SETOFF 20
C EVAL A35_A1='YARRYY'
C EVAL A35_A2='Y'
C EVAL $A=3
C A35_A2 SCAN A35_A1:$A A35_AR2 20
C EVAL £DBG_Str=
C 'A35_AR2(01)('+%CHAR(A35_AR2(01))+') '
C +'A35_AR2(02)('+%CHAR(A35_AR2(02))+') '
C +'A35_AR2(03)('+%CHAR(A35_AR2(03))+') '
C +'IN20('+%CHAR(*IN20)+')'

C £DBG_Str DSPLY

0 comments on commit f13df5a

Please sign in to comment.