Find all symmetry operations of a structure (SOFI algorithm).
188 {
190#ifdef WITH_IRA
192
193
194 std::lock_guard<std::mutex> lock(res.library_mutex);
195
196 try {
197 res.require_loaded();
198 } catch (const std::exception &e) {
199 result.error = -1;
200 return result;
201 }
202
204 std::vector<int> typ(nat);
206 for (int i = 0; i < nat; i++)
207 typ[i] = nrs[i];
208
209
211 Eigen::Map<const AtomMatrixF> coords_map(pos.data(), 3, nat);
212
213
214 int nmax = res.get_get_nmax_fn()();
215
216 int n_mat = 0;
217 std::vector<double> mat_buf(9 * nmax);
218 std::vector<int> perm_buf(nat * nmax);
219 std::vector<char> op_buf(nmax + 1);
220 std::vector<int> n_buf(nmax);
221 std::vector<int> p_buf(nmax);
222 std::vector<double> ax_buf(3 * nmax);
223 std::vector<double> angle_buf(nmax);
224 std::vector<double> dH_buf(nmax);
225 std::vector<char> pg_buf(11);
226 int n_prin_ax = 0;
227 std::vector<double> prin_ax_buf(3 * nmax);
228 int cerr = 0;
229
230 double *mat_data = mat_buf.data();
231 int *perm_data = perm_buf.data();
232 char *op_data = op_buf.data();
233 int *n_data = n_buf.data();
234 int *p_data = p_buf.data();
235 double *ax_data = ax_buf.data();
236 double *angle_data = angle_buf.data();
237 double *dH_data = dH_buf.data();
238 char *pg = pg_buf.data();
239 double *prin_ax = prin_ax_buf.data();
240
241 res.get_compute_all_fn()(nat, typ.data(), coords_map.data(), threshold,
242 prescreenIh ? 1 : 0, &n_mat, &mat_data, &perm_data,
243 &op_data, &n_data, &p_data, &ax_data, &angle_data,
244 &dH_data, &pg, &n_prin_ax, &prin_ax, &cerr);
245
246 result.error = cerr;
247 if (cerr == 0) {
248 result.nOperations = n_mat;
249 if (pg) {
250 result.pointGroup = std::string(pg);
251 }
252
253 result.operations.resize(n_mat);
254 for (int k = 0; k < n_mat; k++) {
255 Eigen::Map<const Matrix3d> op_map(&mat_data[k * 9]);
256 result.operations[k] =
257 op_map.transpose();
258 }
259
260 if (angle_data) {
261 result.angles.assign(angle_data, angle_data + n_mat);
262 }
263 if (ax_data) {
264 result.axes.resize(n_mat);
265 for (int k = 0; k < n_mat; k++) {
266 result.axes[k] = Eigen::Map<const Vector3d>(&ax_data[k * 3]);
267 }
268 }
269 }
270
271
272
273
274
275 if (mat_data != mat_buf.data())
276 std::free(mat_data);
277 if (perm_data != perm_buf.data())
278 std::free(perm_data);
279 if (op_data != op_buf.data())
280 std::free(op_data);
281 if (n_data != n_buf.data())
282 std::free(n_data);
283 if (p_data != p_buf.data())
284 std::free(p_data);
285 if (ax_data != ax_buf.data())
286 std::free(ax_data);
287 if (angle_data != angle_buf.data())
288 std::free(angle_data);
289 if (dH_data != dH_buf.data())
290 std::free(dH_data);
291 if (pg != pg_buf.data())
292 std::free(pg);
293 if (prin_ax != prin_ax_buf.data())
294 std::free(prin_ax);
295#else
296 result.error = -1;
297#endif
298 return result;
299}
Eigen::Matrix< double, Eigen::Dynamic, 3, eOnStorageOrder > AtomMatrix
VectorXi getAtomicNrs() const
long int numberOfAtoms() const
const AtomMatrix & getPositions() const
IRAResource & get_ira_resource()
Global access to thread-safe IRA resource.