1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185 | --
-- Copyright (C) 2024, Vadim Godunko <vgodunko@gmail.com>
--
-- SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
--
pragma Restrictions (No_Elaboration_Code);
pragma Ada_2022;
with Interfaces;
with System.Storage_Elements;
with System_ARMv7M.SCB;
with System_Types;
package body System_ARMv7M.Startup_Utilities is
procedure Copy
(Start_Address : System.Address;
End_Address : System.Address;
Load_Address : System.Address);
-- Copy data starting from Load_Address to the memory region at
-- Start_Address .. End_Address-4.
procedure Fill
(Start_Address : System.Address;
End_Address : System.Address);
-- Fill memory at Start_Address .. End_Address-4 by zero.
----------
-- Copy --
----------
procedure Copy
(Start_Address : System.Address;
End_Address : System.Address;
Load_Address : System.Address)
is
use type System.Address;
use type System.Storage_Elements.Storage_Offset;
Source_Address : System.Address := Load_Address;
Destination_Address : System.Address := Start_Address;
begin
if Source_Address /= Destination_Address then
while Destination_Address /= End_Address loop
declare
Source : constant Interfaces.Unsigned_32
with Import, Address => Source_Address;
Destination : Interfaces.Unsigned_32
with Import, Address => Destination_Address;
begin
Destination := Source;
Source_Address :=
@ + Interfaces.Unsigned_32'Max_Size_In_Storage_Elements;
Destination_Address :=
@ + Interfaces.Unsigned_32'Max_Size_In_Storage_Elements;
end;
end loop;
end if;
end Copy;
-----------------------
-- Copy_Data_Section --
-----------------------
procedure Copy_Data_Section is
sidata : constant System.Storage_Elements.Integer_Address
with Import, Convention => C, External_Name => "_sidata";
sdata : constant System.Storage_Elements.Integer_Address
with Import, Convention => C, External_Name => "_sdata";
edata : constant System.Storage_Elements.Integer_Address
with Import, Convention => C, External_Name => "_edata";
begin
Copy (sdata'Address, edata'Address, sidata'Address);
end Copy_Data_Section;
----------------------------
-- Copy_DTCM_Data_Section --
----------------------------
procedure Copy_DTCM_Data_Section is
siitcmtext : constant System_Types.Unsigned_32
with Import, Convention => C, External_Name => "_siitcmtext";
sitcmtext : constant System_Types.Unsigned_32
with Import, Convention => C, External_Name => "_sitcmtext";
eitcmtext : constant System_Types.Unsigned_32
with Import, Convention => C, External_Name => "_eitcmtext";
begin
Copy (sitcmtext'Address, eitcmtext'Address, siitcmtext'Address);
end Copy_DTCM_Data_Section;
----------------------------
-- Copy_ITCM_Text_Section --
----------------------------
procedure Copy_ITCM_Text_Section is
sidtcmdata : constant System_Types.Unsigned_32
with Import, Convention => C, External_Name => "_sidtcmdata";
sdtcmdata : constant System_Types.Unsigned_32
with Import, Convention => C, External_Name => "_sdtcmdata";
edtcmdata : constant System_Types.Unsigned_32
with Import, Convention => C, External_Name => "_edtcmdata";
begin
Copy (sdtcmdata'Address, edtcmdata'Address, sidtcmdata'Address);
end Copy_ITCM_Text_Section;
----------------
-- Enable_FPU --
----------------
procedure Enable_FPU is
Aux : SCB.SCB_CPACR_Register := SCB.SCB.CPACR;
begin
Aux.CP10 := 2#11#;
Aux.CP11 := 2#11#;
SCB.SCB.CPACR := Aux;
end Enable_FPU;
----------
-- Fill --
----------
procedure Fill
(Start_Address : System.Address;
End_Address : System.Address)
is
use type System.Address;
use type System.Storage_Elements.Storage_Offset;
Destination_Address : System.Address := Start_Address;
begin
while Destination_Address /= End_Address loop
declare
Destination : Interfaces.Unsigned_32
with Import, Address => Destination_Address;
begin
Destination := 0;
Destination_Address :=
@ + Interfaces.Unsigned_32'Max_Size_In_Storage_Elements;
end;
end loop;
end Fill;
----------------------
-- Fill_BSS_Section --
----------------------
procedure Fill_BSS_Section is
sbss : constant System_Types.Unsigned_32
with Import, Convention => C, External_Name => "_sbss";
ebss : constant System_Types.Unsigned_32
with Import, Convention => C, External_Name => "_ebss";
begin
Fill (sbss'Address, ebss'Address);
end Fill_BSS_Section;
---------------------------
-- Fill_DTCM_BSS_Section --
---------------------------
procedure Fill_DTCM_BSS_Section is
sdtcmbss : constant System_Types.Unsigned_32
with Import, Convention => C, External_Name => "_sdtcmbss";
edtcmbss : constant System_Types.Unsigned_32
with Import, Convention => C, External_Name => "_edtcmbss";
begin
Fill (sdtcmbss'Address, edtcmbss'Address);
end Fill_DTCM_BSS_Section;
end System_ARMv7M.Startup_Utilities;
|