Skip to content

Commit

Permalink
Range() calls must always be unmarked
Browse files Browse the repository at this point in the history
  • Loading branch information
jbardin committed Oct 11, 2023
1 parent 367822e commit 14b68b0
Show file tree
Hide file tree
Showing 2 changed files with 29 additions and 8 deletions.
23 changes: 15 additions & 8 deletions hclsyntax/expression.go
Original file line number Diff line number Diff line change
Expand Up @@ -721,18 +721,24 @@ func (e *ConditionalExpr) Value(ctx *hcl.EvalContext) (cty.Value, hcl.Diagnostic
if trueResult.Type().IsCollectionType() && falseResult.Type().IsCollectionType() {
if trueResult.Type().Equals(falseResult.Type()) {
if !(trueResult.IsNull() || falseResult.IsNull()) {
trueLen := trueResult.Length()
falseLen := falseResult.Length()
if gt := trueLen.GreaterThan(falseLen); gt.IsKnown() {
// the bounds are not part of the final result value, so
// the marks are not needed
tr, _ := trueResult.Unmark()
fr, _ := falseResult.Unmark()
trueRange := tr.Range()
falseRange := fr.Range()

if gt := trueResult.Length().GreaterThan(falseResult.Length()); gt.IsKnown() {
gt, _ := gt.Unmark()
b := cty.UnknownVal(resultType).Refine()
if gt.True() {
b = b.
CollectionLengthLowerBound(falseResult.Range().LengthLowerBound()).
CollectionLengthUpperBound(trueResult.Range().LengthUpperBound())
CollectionLengthLowerBound(falseRange.LengthLowerBound()).
CollectionLengthUpperBound(trueRange.LengthUpperBound())
} else {
b = b.
CollectionLengthLowerBound(trueResult.Range().LengthLowerBound()).
CollectionLengthUpperBound(falseResult.Range().LengthUpperBound())
CollectionLengthLowerBound(trueRange.LengthLowerBound()).
CollectionLengthUpperBound(falseRange.LengthUpperBound())
}
b = b.NotNull() // If neither of the results is null then the result can't be either
return b.NewValue().WithSameMarks(condResult).WithSameMarks(trueResult).WithSameMarks(falseResult), diags
Expand Down Expand Up @@ -1740,7 +1746,8 @@ func (e *SplatExpr) Value(ctx *hcl.EvalContext) (cty.Value, hcl.Diagnostics) {
if ty.IsListType() && sourceVal.Type().IsCollectionType() {
// We can refine the length of an unknown list result based on
// the source collection's own length.
sourceRng := sourceVal.Range()
sv, _ := sourceVal.Unmark()
sourceRng := sv.Range()
ret = ret.Refine().
CollectionLengthLowerBound(sourceRng.LengthLowerBound()).
CollectionLengthUpperBound(sourceRng.LengthUpperBound()).
Expand Down
14 changes: 14 additions & 0 deletions hclsyntax/expression_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -1971,6 +1971,20 @@ EOT
cty.UnknownVal(cty.Set(cty.String)).Refine().NotNull().CollectionLengthLowerBound(1).CollectionLengthUpperBound(4).NewValue(), // deduced through refinements
0,
},
{
`unknown ? amr : bmr`,
&hcl.EvalContext{
Variables: map[string]cty.Value{
"unknown": cty.UnknownVal(cty.Bool),
"amr": cty.UnknownVal(cty.Set(cty.String)).Mark("test").Refine().
CollectionLengthLowerBound(1).CollectionLengthUpperBound(2).NewValue(),
"bmr": cty.UnknownVal(cty.Set(cty.String)).Mark("test").Refine().
CollectionLengthLowerBound(3).CollectionLengthUpperBound(4).NewValue(),
},
},
cty.UnknownVal(cty.Set(cty.String)).Refine().NotNull().CollectionLengthLowerBound(1).CollectionLengthUpperBound(4).NewValue().Mark("test"), // deduced through refinements
0,
},
{
`unknown ? a : b`,
&hcl.EvalContext{
Expand Down

0 comments on commit 14b68b0

Please sign in to comment.