STIR 6.4.0
InputFileFormatRegistry.txx
1//
2//
3/*
4 Copyright (C) 2006- 2011, Hammersmith Imanet Ltd
5 This file is part of STIR.
6 SPDX-License-Identifier: Apache-2.0
7
8 See STIR/LICENSE.txt for details
9*/
10/*!
11 \file
12 \ingroup IO
13 \brief Implementation of class stir::InputFileFormatRegistry
14
15 This file provides the implementations of the template class
16 stir::InputFileFormatRegistry. It has to be included by a .cxx
17 file that needs to instantiate this class.
18
19 \author Kris Thielemans
20
21*/
22
23#include "stir/IO/InputFileFormatRegistry.h"
24#include "stir/IO/FileSignature.h"
25#include "stir/utilities.h" // for open_read_binary
26#include "stir/error.h"
27#include <utility> // for make_pair
28#include <typeinfo>
29
30START_NAMESPACE_STIR
31
32template <class DataT>
33shared_ptr<InputFileFormatRegistry<DataT>>&
34InputFileFormatRegistry<DataT>::default_sptr()
35{
36 /* Implementation note:
37 It is safer to have a static member inside this function than
38 to have a static member of the class. The reason for this is
39 that there is no guarantee on the order in which static
40 class members are initialised. So, if other static initialisers
41 would call default_sptr(), we wouldn't be sure if the current
42 _default_sptr is already initialised.
43 With the current implementation, there is no such problem
44 (except potentially in threaded cases. You have to make sure
45 that this function is called once before starting any threads).
46
47 Note that this function cannot be inline because the static member
48 should be initialised in one translation unit only.
49 */
50 static shared_ptr<InputFileFormatRegistry<DataT>> _default_sptr(new InputFileFormatRegistry<DataT>);
51
52 // std::cerr<< "\ndefault_sptr value " << _default_sptr.get() << std::endl;
53 return _default_sptr;
54}
55
56template <class DataT>
57void
58InputFileFormatRegistry<DataT>::add_to_registry(FactorySPtr const& factory, const unsigned ranking)
59{
60 this->_registry.insert(std::make_pair(ranking, factory));
61}
62
63template <class DataT>
64void
65InputFileFormatRegistry<DataT>::remove_from_registry(const Factory& factory)
66{
67 iterator iter = this->_registry.begin();
68 iterator const end = this->_registry.end();
69 while (iter != end)
70 {
71 if (typeid(*iter->second) == typeid(factory))
72 {
73 this->_registry.erase(iter);
74 return;
75 }
76 ++iter;
77 }
78}
79
80template <class DataT>
81typename InputFileFormatRegistry<DataT>::Factory const&
82InputFileFormatRegistry<DataT>::find_factory(const FileSignature& signature, std::istream& input) const
83{
84 const_iterator iter = this->_actual_find_factory(signature, input);
85 if (this->_valid(iter))
86 return *(iter->second);
87 else
88 {
89 std::cerr << "Available input file formats:\n";
90 this->list_registered_names(std::cerr);
91 error("no file format found that can read this data");
92 }
93 // we never get here, but most compilers will complain here
94 // so we 'return' a bogus factory
95 return (*iter->second);
96}
97
98template <class DataT>
99typename InputFileFormatRegistry<DataT>::Factory const&
100InputFileFormatRegistry<DataT>::find_factory(const FileSignature& signature, const std::string& filename) const
101{
102 const_iterator iter = this->_actual_find_factory(signature, filename);
103 if (this->_valid(iter))
104 return *(iter->second);
105 else
106 {
107 std::cerr << "Available input file formats:\n";
108 this->list_registered_names(std::cerr);
109 error("no file format found that can read file '%s'", filename.c_str());
110 }
111 // we never get here, but most compilers will complain here
112 // so we 'return' a bogus factory
113 return (*iter->second);
114}
115
116template <class DataT>
117typename InputFileFormatRegistry<DataT>::Factory const&
118InputFileFormatRegistry<DataT>::find_factory(const std::string& filename) const
119{
120 return this->find_factory(FileSignature(filename), filename);
121}
122
123template <class DataT>
124typename InputFileFormatRegistry<DataT>::Factory const&
125InputFileFormatRegistry<DataT>::find_factory(std::istream& input) const
126{
127 return this->find_factory(FileSignature(input), input);
128}
129
130template <class DataT>
131void
132InputFileFormatRegistry<DataT>::list_registered_names(std::ostream& stream) const
133{
134 const_iterator iter = this->_registry.begin();
135 const_iterator const end = this->_registry.end();
136 while (iter != end)
137 {
138 stream << iter->second->get_name() << '\n';
139 ++iter;
140 }
141}
142
143END_NAMESPACE_STIR