1 | /* |
2 | * debug.hpp |
3 | * |
4 | * Created on: Oct 17, 2018 |
5 | * Author: i-bird |
6 | */ |
7 | |
8 | #ifndef DEBUG_HPP_ |
9 | #define DEBUG_HPP_ |
10 | |
11 | enum debug_run |
12 | { |
13 | HOST, |
14 | DEVICE |
15 | }; |
16 | |
17 | enum debug_iterator |
18 | { |
19 | DOMAIN_IT, |
20 | DOMAIN_GHOST_IT, |
21 | GHOST_IT, |
22 | }; |
23 | |
24 | |
25 | |
26 | /*! \brief Find in a vector dist particles if "certain conditions" |
27 | * |
28 | * This function in in general used to debug. Many time in order to discover problem we want to control if particles/grid points has zeros or out of range values. |
29 | * You can implement these check, by creating the loops manually or using the function debug_find with a lambda function. |
30 | * |
31 | * |
32 | * @param vd distributed vector |
33 | * @param fun_test function that define the test |
34 | * @param fun_print function to print a message |
35 | * @param it iterator type domain, domain + ghost, ghost |
36 | * @param type_of_run optionally can do the scan on device |
37 | * |
38 | * /return This function return true if the debug function has been triggered |
39 | * |
40 | */ |
41 | template<typename vector_dist_type, typename functor_test, typename functor_print> |
42 | bool debug_find(vector_dist_type & vd, functor_test fun_test, functor_print fun_print, |
43 | debug_iterator it = debug_iterator::DOMAIN_IT, debug_run type_of_run = debug_run::HOST, |
44 | bool print = true) |
45 | { |
46 | vector_dist_iterator ite(0,0); |
47 | |
48 | if (it == debug_iterator::DOMAIN_IT) |
49 | {ite = vd.getDomainIterator();} |
50 | else if (it == debug_iterator::DOMAIN_GHOST_IT) |
51 | {ite = vd.getDomainAndGhostIterator();} |
52 | else |
53 | {ite = vd.getGhostIterator();} |
54 | |
55 | bool test_tot = false; |
56 | |
57 | while (ite.isNext()) |
58 | { |
59 | bool test = fun_test(ite.get().getKey()); |
60 | test_tot |= test; |
61 | |
62 | if (test == true && print == true) |
63 | {std::cout << fun_print(ite.get().getKey()) << std::endl;} |
64 | |
65 | ++ite; |
66 | } |
67 | |
68 | return test_tot; |
69 | } |
70 | |
71 | /*! \brief Find in a vector dist particles if "certain conditions" |
72 | * |
73 | * This function in in general used to debug. Many time in order to discover problem we want to control if particles/grid points has zeros or out of range values. |
74 | * You can implement these check, by creating the loops manually or using the function debug_find with a lambda function. |
75 | * |
76 | * |
77 | * @param vd distributed vector |
78 | * @param fun_test function that define the test |
79 | * @param fun_print function to print a message |
80 | * @param it iterator type domain, domain + ghost, ghost |
81 | * @param type_of_run optionally can do the scan on device |
82 | * |
83 | * /return This function return true if the debug function has been triggered |
84 | * |
85 | */ |
86 | template<typename vector_type, typename functor_test, typename functor_print> |
87 | bool debug_find_single(vector_type vd, functor_test fun_test, functor_print fun_print, |
88 | size_t g_m, debug_iterator it = debug_iterator::DOMAIN_IT, debug_run type_of_run = debug_run::HOST, |
89 | bool print = true) |
90 | { |
91 | openfpm::vector_key_iterator ite(0,0); |
92 | |
93 | if (it == debug_iterator::DOMAIN_IT) |
94 | {ite = vd.getIteratorTo(g_m);} |
95 | else if (it == debug_iterator::DOMAIN_GHOST_IT) |
96 | {ite = vd.getIterator();} |
97 | else |
98 | {ite = vd.getIteratorFrom(g_m);} |
99 | |
100 | bool test_tot = false; |
101 | |
102 | while (ite.isNext()) |
103 | { |
104 | bool test = fun_test(ite.get()); |
105 | test_tot |= test; |
106 | |
107 | if (test == true && print == true) |
108 | {std::cout << fun_print(ite.get()) << std::endl;} |
109 | |
110 | ++ite; |
111 | } |
112 | |
113 | return test_tot; |
114 | } |
115 | |
116 | /*! \brief scan for a particle inside a box |
117 | * |
118 | * |
119 | * \param vd vector_dist |
120 | * \param box box |
121 | * \param it iterator type |
122 | * \param type_of_run check host or device memory |
123 | * \return true if one or more is detected |
124 | */ |
125 | template<typename vector_dist_type> |
126 | bool debug_is_in_box(vector_dist_type & vd, Box<vector_dist_type::dims, typename vector_dist_type::stype> box, |
127 | debug_iterator it = debug_iterator::DOMAIN_IT, debug_run type_of_run = debug_run::HOST, |
128 | bool print = true) |
129 | { |
130 | auto fun_test = [&vd,&box](unsigned int p){return box.isInside(vd.getPos(p));}; |
131 | auto fun_print = [&vd,&box](unsigned int p) |
132 | { |
133 | std::stringstream message; |
134 | message << "Debug info: detected particle p=" << p << " inside box: " << box.toString() << std::endl; |
135 | return message.str(); |
136 | }; |
137 | |
138 | return debug_find(vd,fun_test,fun_print,it,type_of_run,print); |
139 | } |
140 | |
141 | |
142 | /*! \brief scan for a particle inside a box |
143 | * |
144 | * |
145 | * \param vd vector_dist |
146 | * \param box box |
147 | * \param it iterator type |
148 | * \param type_of_run check host or device memory |
149 | * \return true if one or more is detected |
150 | */ |
151 | template<typename vector_type> |
152 | bool debug_is_in_box_single(vector_type & vd, Box<vector_type::value_type::dims, typename vector_type::value_type::coord_type> box, |
153 | size_t g_m, std::string message = std::string() , debug_iterator it = debug_iterator::DOMAIN_IT, debug_run type_of_run = debug_run::HOST, |
154 | bool print = true) |
155 | { |
156 | auto fun_test = [&vd,&box](unsigned int p){return box.isInside(vd.template get<0>(p));}; |
157 | auto fun_print = [&vd,&box,&message](unsigned int p) |
158 | { |
159 | std::stringstream message_srm; |
160 | message_srm << "Debug info: " << message << " detected particle p=" << p << " inside box: " << box.toString() << std::endl; |
161 | return message_srm.str(); |
162 | }; |
163 | |
164 | return debug_find_single(vd,fun_test,fun_print,g_m,it,type_of_run,print); |
165 | } |
166 | |
167 | #endif /* DEBUG_HPP_ */ |
168 | |