Skip to content

Commit c50ded3

Browse files
Copilotmballance
andcommitted
Add comprehensive test coverage for rangelist edge cases
Co-authored-by: mballance <1340805+mballance@users.noreply.github.com>
1 parent fe5d3b1 commit c50ded3

File tree

3 files changed

+187
-1
lines changed

3 files changed

+187
-1
lines changed

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -111,3 +111,4 @@ junit/
111111
.venv/
112112
.venv.bld
113113
cov.xml
114+
/src/pyucis

src/pyucis

Lines changed: 0 additions & 1 deletion
This file was deleted.
Lines changed: 186 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,186 @@
1+
'''
2+
Created on 2026-02-03
3+
4+
Extended test cases for rangelist constraints with unsolvable scenarios
5+
Tests various edge cases to ensure robust error handling
6+
'''
7+
import unittest
8+
from vsc_test_case import VscTestCase
9+
import vsc
10+
11+
class TestConstraintRangelistExtended(VscTestCase):
12+
13+
def test_rangelist_tuple_empty_domain(self):
14+
"""Test tuple syntax with completely empty domain after constraint propagation"""
15+
16+
@vsc.randobj
17+
class C():
18+
def __init__(self):
19+
self.a = vsc.rand_uint8_t()
20+
21+
@vsc.constraint
22+
def constr(self):
23+
self.a > 255 # Impossible for uint8_t
24+
25+
c = C()
26+
with self.assertRaises(vsc.SolveFailure):
27+
with c.randomize_with() as it:
28+
it.a in vsc.rangelist((0, 10))
29+
30+
def test_rangelist_multiple_tuples_unsolvable(self):
31+
"""Test multiple tuple ranges with unsolvable constraints"""
32+
33+
@vsc.randobj
34+
class C():
35+
def __init__(self):
36+
self.a = vsc.rand_uint8_t()
37+
38+
@vsc.constraint
39+
def constr(self):
40+
self.a > 200
41+
42+
c = C()
43+
with self.assertRaises(vsc.SolveFailure):
44+
with c.randomize_with() as it:
45+
it.a in vsc.rangelist((0, 50), (51, 100), (101, 150))
46+
47+
def test_rangelist_single_value_tuple_unsolvable(self):
48+
"""Test single value tuple (range of one) with unsolvable constraint"""
49+
50+
@vsc.randobj
51+
class C():
52+
def __init__(self):
53+
self.a = vsc.rand_uint8_t()
54+
55+
@vsc.constraint
56+
def constr(self):
57+
self.a > 100
58+
59+
c = C()
60+
with self.assertRaises(vsc.SolveFailure):
61+
with c.randomize_with() as it:
62+
it.a in vsc.rangelist((50, 50))
63+
64+
def test_rangelist_boundary_tuple_unsolvable(self):
65+
"""Test boundary conditions with tuple syntax"""
66+
67+
@vsc.randobj
68+
class C():
69+
def __init__(self):
70+
self.a = vsc.rand_uint8_t()
71+
72+
@vsc.constraint
73+
def constr(self):
74+
self.a < 10
75+
76+
c = C()
77+
with self.assertRaises(vsc.SolveFailure):
78+
with c.randomize_with() as it:
79+
it.a in vsc.rangelist((200, 255))
80+
81+
def test_rangelist_mixed_syntax_unsolvable(self):
82+
"""Test mixed tuple and range syntax with unsolvable constraints"""
83+
84+
@vsc.randobj
85+
class C():
86+
def __init__(self):
87+
self.a = vsc.rand_uint8_t()
88+
89+
@vsc.constraint
90+
def constr(self):
91+
self.a > 150
92+
93+
c = C()
94+
with self.assertRaises(vsc.SolveFailure):
95+
with c.randomize_with() as it:
96+
it.a in vsc.rangelist((0, 50), 75, (100, 120))
97+
98+
def test_rangelist_tuple_overlapping_with_constraint(self):
99+
"""Test tuple syntax where constraint narrows to empty set"""
100+
101+
@vsc.randobj
102+
class C():
103+
def __init__(self):
104+
self.a = vsc.rand_uint8_t()
105+
106+
@vsc.constraint
107+
def constr(self):
108+
self.a > 100
109+
self.a < 90 # Impossible: a cannot be both > 100 and < 90
110+
111+
c = C()
112+
with self.assertRaises(vsc.SolveFailure):
113+
c.randomize()
114+
115+
def test_rangelist_tuple_zero_based_range_unsolvable(self):
116+
"""Test tuple with zero-based range and unsolvable constraint"""
117+
118+
@vsc.randobj
119+
class C():
120+
def __init__(self):
121+
self.a = vsc.rand_uint8_t()
122+
123+
@vsc.constraint
124+
def constr(self):
125+
self.a > 100
126+
127+
c = C()
128+
with self.assertRaises(vsc.SolveFailure):
129+
with c.randomize_with() as it:
130+
it.a in vsc.rangelist((0, 0))
131+
132+
def test_rangelist_tuple_max_value_unsolvable(self):
133+
"""Test tuple with maximum value and unsolvable constraint"""
134+
135+
@vsc.randobj
136+
class C():
137+
def __init__(self):
138+
self.a = vsc.rand_uint8_t()
139+
140+
@vsc.constraint
141+
def constr(self):
142+
self.a < 128
143+
144+
c = C()
145+
with self.assertRaises(vsc.SolveFailure):
146+
with c.randomize_with() as it:
147+
it.a in vsc.rangelist((255, 255))
148+
149+
def test_rangelist_tuple_success_case(self):
150+
"""Verify tuple syntax works correctly when constraints are solvable"""
151+
152+
@vsc.randobj
153+
class C():
154+
def __init__(self):
155+
self.a = vsc.rand_uint8_t()
156+
157+
@vsc.constraint
158+
def constr(self):
159+
self.a > 100
160+
161+
c = C()
162+
# This should succeed
163+
with c.randomize_with() as it:
164+
it.a in vsc.rangelist((120, 150))
165+
166+
# Verify the value is within the expected range
167+
self.assertGreaterEqual(c.a, 120)
168+
self.assertLessEqual(c.a, 150)
169+
self.assertGreater(c.a, 100)
170+
171+
def test_rangelist_multiarg_empty_domain(self):
172+
"""Test multi-arg syntax with completely empty domain (baseline)"""
173+
174+
@vsc.randobj
175+
class C():
176+
def __init__(self):
177+
self.a = vsc.rand_uint8_t()
178+
179+
@vsc.constraint
180+
def constr(self):
181+
self.a > 255 # Impossible for uint8_t
182+
183+
c = C()
184+
with self.assertRaises(vsc.SolveFailure):
185+
with c.randomize_with() as it:
186+
it.a in vsc.rangelist(0, 10)

0 commit comments

Comments
 (0)