Coverage for hdl_registers/generator/vhdl/simulation/test/test_read_write_package.py: 100%

56 statements  

« prev     ^ index     » next       coverage.py v7.6.8, created at 2024-12-01 20:50 +0000

1# -------------------------------------------------------------------------------------------------- 

2# Copyright (c) Lukas Vik. All rights reserved. 

3# 

4# This file is part of the hdl-registers project, an HDL register generator fast enough to run 

5# in real time. 

6# https://hdl-registers.com 

7# https://github.com/hdl-registers/hdl-registers 

8# -------------------------------------------------------------------------------------------------- 

9 

10""" 

11Some limited unit tests. 

12Note that the generated VHDL code is also simulated in a functional test. 

13""" 

14 

15# Third party libraries 

16from tsfpga.system_utils import read_file 

17 

18# First party libraries 

19from hdl_registers.field.numerical_interpretation import ( 

20 Signed, 

21 SignedFixedPoint, 

22 Unsigned, 

23 UnsignedFixedPoint, 

24) 

25from hdl_registers.generator.vhdl.simulation.read_write_package import ( 

26 VhdlSimulationReadWritePackageGenerator, 

27) 

28from hdl_registers.register_list import RegisterList 

29from hdl_registers.register_modes import REGISTER_MODES 

30 

31 

32def test_package_is_not_generated_without_registers(tmp_path): 

33 register_list = RegisterList(name="test", source_definition_file=None) 

34 

35 assert not VhdlSimulationReadWritePackageGenerator(register_list, tmp_path).create().exists() 

36 

37 register_list.add_constant(name="apa", value=True, description="") 

38 assert not VhdlSimulationReadWritePackageGenerator(register_list, tmp_path).create().exists() 

39 

40 register_list.append_register(name="hest", mode=REGISTER_MODES["r_w"], description="") 

41 assert VhdlSimulationReadWritePackageGenerator(register_list, tmp_path).create().exists() 

42 

43 

44def test_re_generating_package_without_registers_should_delete_old_file(tmp_path): 

45 register_list = RegisterList(name="test", source_definition_file=None) 

46 register_list.append_register(name="apa", mode=REGISTER_MODES["r_w"], description="") 

47 

48 assert VhdlSimulationReadWritePackageGenerator(register_list, tmp_path).create().exists() 

49 

50 register_list.register_objects = [] 

51 assert not VhdlSimulationReadWritePackageGenerator(register_list, tmp_path).create().exists() 

52 

53 

54def test_read_write_as_integer(tmp_path): 

55 register_list = RegisterList(name="caesar", source_definition_file=None) 

56 

57 register_list.append_register(name="empty", mode=REGISTER_MODES["r_w"], description="") 

58 

59 register = register_list.append_register( 

60 name="full", mode=REGISTER_MODES["r_w"], description="" 

61 ) 

62 register.append_bit(name="my_bit", description="", default_value="0") 

63 register.append_enumeration( 

64 name="my_enumeration", 

65 description="", 

66 elements={"first": "", "second": ""}, 

67 default_value="first", 

68 ) 

69 register.append_integer( 

70 name="my_integer", description="", min_value=0, max_value=127, default_value=0 

71 ) 

72 register.append_bit_vector( 

73 name="my_signed_bit_vector", 

74 description="", 

75 width=4, 

76 default_value="0000", 

77 numerical_interpretation=Signed(bit_width=4), 

78 ) 

79 register.append_bit_vector( 

80 name="my_sfixed_bit_vector", 

81 description="", 

82 width=4, 

83 default_value="0000", 

84 numerical_interpretation=SignedFixedPoint(1, -2), 

85 ) 

86 register.append_bit_vector( 

87 name="my_unsigned_bit_vector", 

88 description="", 

89 width=4, 

90 default_value="0000", 

91 numerical_interpretation=Unsigned(bit_width=4), 

92 ) 

93 register.append_bit_vector( 

94 name="my_ufixed_bit_vector", 

95 description="", 

96 width=4, 

97 default_value="0000", 

98 numerical_interpretation=UnsignedFixedPoint(1, -2), 

99 ) 

100 

101 vhdl = read_file(VhdlSimulationReadWritePackageGenerator(register_list, tmp_path).create()) 

102 

103 def check_access_as_named_type(direction: str, type_name: str, name: str) -> None: 

104 assert direction in ["read", "write"] 

105 in_or_out = "in" if direction == "write" else "out" 

106 expected = f""" 

107 procedure {direction}_caesar_{name}( 

108 signal net : inout network_t; 

109 value : {in_or_out} {type_name}; 

110""" 

111 return expected in vhdl 

112 

113 def check_access_as_integer(direction: str, name: str) -> None: 

114 return check_access_as_named_type(direction=direction, type_name="integer", name=name) 

115 

116 def check_access_as_slv(direction: str, name: str) -> None: 

117 return check_access_as_named_type(direction=direction, type_name="reg_t", name=name) 

118 

119 def check_access_as_native(direction: str, name: str) -> None: 

120 return check_access_as_named_type( 

121 direction=direction, type_name=f"caesar_{name}_t", name=name 

122 ) 

123 

124 for direction in ["read", "write"]: 

125 assert check_access_as_integer(direction=direction, name="empty") 

126 assert check_access_as_slv(direction=direction, name="empty") 

127 # Empty register does not have a native record type. 

128 assert not check_access_as_native(direction=direction, name="empty") 

129 

130 assert check_access_as_integer(direction=direction, name="full") 

131 # Register with fields does not have a write as SLV function. 

132 assert check_access_as_slv(direction=direction, name="full") == (direction == "read") 

133 assert check_access_as_native(direction=direction, name="full") 

134 

135 # Only non-fractional vector types shall have the possibility of accessing as integer. 

136 assert check_access_as_integer(direction=direction, name="full_my_signed_bit_vector") 

137 assert check_access_as_native(direction=direction, name="full_my_signed_bit_vector") 

138 assert check_access_as_integer(direction=direction, name="full_my_unsigned_bit_vector") 

139 assert not check_access_as_integer(direction=direction, name="full_my_ufixed_bit_vector") 

140 assert not check_access_as_integer(direction=direction, name="full_my_sfixed_bit_vector") 

141 assert not check_access_as_integer(direction=direction, name="full_my_bit") 

142 assert not check_access_as_integer(direction=direction, name="full_my_enumeration") 

143 assert not check_access_as_integer(direction=direction, name="full_my_integer")