Skip to content

Commit 40a69d7

Browse files
author
Remi Delmas
committed
CONTRACTS: loop info tagging utility functions
Utility functions for loop contracts instrumentation, allowing to tag GOTO instructions with loop identifiers and loop instruction type.
1 parent b34e991 commit 40a69d7

File tree

3 files changed

+182
-0
lines changed

3 files changed

+182
-0
lines changed

src/goto-instrument/Makefile

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ SRC = accelerate/accelerate.cpp \
1818
call_sequences.cpp \
1919
contracts/contracts.cpp \
2020
contracts/dynamic-frames/dfcc_utils.cpp \
21+
contracts/dynamic-frames/dfcc_loop_tags.cpp \
2122
contracts/dynamic-frames/dfcc_library.cpp \
2223
contracts/dynamic-frames/dfcc_is_fresh.cpp \
2324
contracts/dynamic-frames/dfcc_pointer_in_range.cpp \
Lines changed: 130 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,130 @@
1+
/*******************************************************************\
2+
3+
Module: Dynamic frame condition checking
4+
5+
Author: Qinheping Hu, [email protected]
6+
7+
Author: Remi Delmas, [email protected]
8+
9+
Date: March 2023
10+
11+
\*******************************************************************/
12+
13+
#include "dfcc_loop_tags.h"
14+
15+
#define ID_LOOP_ID "loop-id"
16+
#define ID_LOOP_HEAD "loop-head"
17+
#define ID_LOOP_BODY "loop-body"
18+
#define ID_LOOP_LATCH "loop-latch"
19+
#define ID_LOOP_EXITING "loop-exiting"
20+
#define ID_LOOP_TOP_LEVEL "loop-top-level"
21+
22+
void dfcc_set_loop_id(
23+
goto_programt::instructiont &instruction,
24+
const std::size_t loop_id)
25+
{
26+
instruction.source_location_nonconst().set(ID_LOOP_ID, loop_id);
27+
}
28+
29+
optionalt<std::size_t>
30+
dfcc_get_loop_id(const goto_programt::instructiont &instruction)
31+
{
32+
if(instruction.source_location().get(ID_LOOP_ID).empty())
33+
return {};
34+
35+
return instruction.source_location().get_size_t(ID_LOOP_ID);
36+
}
37+
38+
bool dfcc_has_loop_id(
39+
const goto_programt::instructiont &instruction,
40+
std::size_t loop_id)
41+
{
42+
auto loop_id_opt = dfcc_get_loop_id(instruction);
43+
return loop_id_opt.has_value() && loop_id_opt.value() == loop_id;
44+
}
45+
46+
static void
47+
dfcc_set_loop_tag(goto_programt::instructiont &instruction, const irep_idt &tag)
48+
{
49+
instruction.source_location_nonconst().set(tag, true);
50+
}
51+
52+
static bool has_loop_tag(
53+
const goto_programt::instructiont &instruction,
54+
const irep_idt &tag)
55+
{
56+
return instruction.source_location().get_bool(tag);
57+
}
58+
59+
void dfcc_set_loop_head(goto_programt::instructiont &instruction)
60+
{
61+
dfcc_set_loop_tag(instruction, ID_LOOP_HEAD);
62+
}
63+
64+
bool dfcc_is_loop_head(const goto_programt::instructiont &instruction)
65+
{
66+
return has_loop_tag(instruction, ID_LOOP_HEAD);
67+
}
68+
69+
void dfcc_set_loop_body(goto_programt::instructiont &instruction)
70+
{
71+
dfcc_set_loop_tag(instruction, ID_LOOP_BODY);
72+
}
73+
74+
bool dfcc_is_loop_body(const goto_programt::instructiont &instruction)
75+
{
76+
return has_loop_tag(instruction, ID_LOOP_BODY);
77+
}
78+
79+
void dfcc_set_loop_exiting(goto_programt::instructiont &instruction)
80+
{
81+
dfcc_set_loop_tag(instruction, ID_LOOP_EXITING);
82+
}
83+
84+
bool dfcc_is_loop_exiting(const goto_programt::instructiont &instruction)
85+
{
86+
return has_loop_tag(instruction, ID_LOOP_EXITING);
87+
}
88+
89+
void dfcc_set_loop_latch(goto_programt::instructiont &instruction)
90+
{
91+
dfcc_set_loop_tag(instruction, ID_LOOP_LATCH);
92+
}
93+
94+
bool dfcc_is_loop_latch(const goto_programt::instructiont &instruction)
95+
{
96+
return has_loop_tag(instruction, ID_LOOP_LATCH);
97+
}
98+
99+
void dfcc_set_loop_top_level(goto_programt::instructiont &instruction)
100+
{
101+
dfcc_set_loop_tag(instruction, ID_LOOP_TOP_LEVEL);
102+
}
103+
104+
bool dfcc_is_loop_top_level(const goto_programt::instructiont &instruction)
105+
{
106+
return has_loop_tag(instruction, ID_LOOP_TOP_LEVEL);
107+
}
108+
109+
void dfcc_remove_loop_tags(goto_programt &goto_program)
110+
{
111+
for(auto &instruction : goto_program.instructions)
112+
{
113+
dfcc_remove_loop_tags(instruction);
114+
}
115+
}
116+
117+
void dfcc_remove_loop_tags(goto_programt::instructiont &instruction)
118+
{
119+
dfcc_remove_loop_tags(instruction.source_location_nonconst());
120+
}
121+
122+
void dfcc_remove_loop_tags(source_locationt &source_location)
123+
{
124+
source_location.remove(ID_LOOP_ID);
125+
source_location.remove(ID_LOOP_HEAD);
126+
source_location.remove(ID_LOOP_BODY);
127+
source_location.remove(ID_LOOP_EXITING);
128+
source_location.remove(ID_LOOP_LATCH);
129+
source_location.remove(ID_LOOP_TOP_LEVEL);
130+
}
Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
/*******************************************************************\
2+
3+
Module: Dynamic frame condition checking
4+
5+
Author: Qinheping Hu, [email protected]
6+
7+
Author: Remi Delmas, [email protected]
8+
9+
Date: March 2023
10+
11+
\*******************************************************************/
12+
13+
/// \file
14+
/// Functions that allow to tag GOTO instructions with loop identifiers and
15+
/// loop instruction type: head, body, exiting, latch.
16+
17+
#ifndef CPROVER_GOTO_INSTRUMENT_CONTRACTS_DYNAMIC_FRAMES_DFCC_LOOP_TAGS_H
18+
#define CPROVER_GOTO_INSTRUMENT_CONTRACTS_DYNAMIC_FRAMES_DFCC_LOOP_TAGS_H
19+
20+
#include <goto-programs/goto_program.h>
21+
22+
void dfcc_set_loop_id(
23+
goto_programt::instructiont &instruction,
24+
std::size_t loop_id);
25+
26+
bool dfcc_has_loop_id(
27+
const goto_programt::instructiont &instruction,
28+
std::size_t loop_id);
29+
30+
optionalt<std::size_t>
31+
dfcc_get_loop_id(const goto_programt::instructiont &instruction);
32+
33+
void dfcc_set_loop_head(goto_programt::instructiont &instruction);
34+
bool dfcc_is_loop_head(const goto_programt::instructiont &instruction);
35+
36+
void dfcc_set_loop_body(goto_programt::instructiont &instruction);
37+
bool dfcc_is_loop_body(const goto_programt::instructiont &instruction);
38+
39+
void dfcc_set_loop_exiting(goto_programt::instructiont &instruction);
40+
bool dfcc_is_loop_exiting(const goto_programt::instructiont &instruction);
41+
42+
void dfcc_set_loop_latch(goto_programt::instructiont &instruction);
43+
bool dfcc_is_loop_latch(const goto_programt::instructiont &instruction);
44+
45+
void dfcc_set_loop_top_level(goto_programt::instructiont &instruction);
46+
bool dfcc_is_loop_top_level(const goto_programt::instructiont &instruction);
47+
48+
void dfcc_remove_loop_tags(goto_programt &goto_program);
49+
void dfcc_remove_loop_tags(goto_programt::instructiont &instruction);
50+
void dfcc_remove_loop_tags(source_locationt &source_location);
51+
#endif

0 commit comments

Comments
 (0)