OpenWalnut  1.2.5
 All Classes Namespaces Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
WProjectFile.cpp
1 //---------------------------------------------------------------------------
2 //
3 // Project: OpenWalnut ( http://www.openwalnut.org )
4 //
5 // Copyright 2009 OpenWalnut Community, BSV@Uni-Leipzig and CNCF@MPI-CBS
6 // For more information see http://www.openwalnut.org/copying
7 //
8 // This file is part of OpenWalnut.
9 //
10 // OpenWalnut is free software: you can redistribute it and/or modify
11 // it under the terms of the GNU Lesser General Public License as published by
12 // the Free Software Foundation, either version 3 of the License, or
13 // (at your option) any later version.
14 //
15 // OpenWalnut is distributed in the hope that it will be useful,
16 // but WITHOUT ANY WARRANTY; without even the implied warranty of
17 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 // GNU Lesser General Public License for more details.
19 //
20 // You should have received a copy of the GNU Lesser General Public License
21 // along with OpenWalnut. If not, see <http://www.gnu.org/licenses/>.
22 //
23 //---------------------------------------------------------------------------
24 
25 #include <fstream>
26 #include <string>
27 #include <vector>
28 
29 #include <boost/regex.hpp>
30 
31 #include "WKernel.h"
32 #include "combiner/WModuleProjectFileCombiner.h"
33 #include "WRoiProjectFileIO.h"
34 #include "../graphicsEngine/WGEProjectFileIO.h"
35 #include "../common/exceptions/WFileNotFound.h"
36 #include "../common/exceptions/WFileOpenFailed.h"
37 
38 #include "WProjectFile.h"
39 
40 WProjectFile::WProjectFile( boost::filesystem::path project ):
43  m_project( project )
44 {
45  // initialize members
46 
47  // The module graph parser
48  m_parsers.push_back( boost::shared_ptr< WProjectFileIO >( new WModuleProjectFileCombiner() ) );
49 
50  // The ROI parser
51  m_parsers.push_back( boost::shared_ptr< WProjectFileIO >( new WRoiProjectFileIO() ) );
52 
53  // The Camera parser
54  m_parsers.push_back( boost::shared_ptr< WProjectFileIO >( new WGEProjectFileIO() ) );
55 }
56 
58 {
59  // cleanup
60  m_parsers.clear();
61 }
62 
63 boost::shared_ptr< WProjectFileIO > WProjectFile::getCameraWriter()
64 {
65  return boost::shared_ptr< WProjectFileIO >( new WGEProjectFileIO() );
66 }
67 
68 boost::shared_ptr< WProjectFileIO > WProjectFile::getModuleWriter()
69 {
70  return boost::shared_ptr< WProjectFileIO >( new WModuleProjectFileCombiner() );
71 }
72 
73 boost::shared_ptr< WProjectFileIO > WProjectFile::getROIWriter()
74 {
75  return boost::shared_ptr< WProjectFileIO >( new WRoiProjectFileIO() );
76 }
77 
79 {
80  // the instance needs to be added here, as it else could be freed before the thread finishes ( remember: it is a shared_ptr ).
81  WKernel::getRunningKernel()->getRootContainer()->addPendingThread( shared_from_this() );
82 
83  // actually run
84  run();
85 }
86 
87 void WProjectFile::save( const std::vector< boost::shared_ptr< WProjectFileIO > >& writer )
88 {
89  wlog::info( "Project File" ) << "Saving project file \"" << m_project.file_string() << "\".";
90 
91  // open the file for write
92  std::ofstream output( m_project.file_string().c_str() );
93  if( !output.is_open() )
94  {
95  throw WFileOpenFailed( std::string( "The project file \"" ) + m_project.file_string() +
96  std::string( "\" could not be opened for write access." ) );
97  }
98 
99  // allow each parser to handle save request
100  for( std::vector< boost::shared_ptr< WProjectFileIO > >::const_iterator iter = writer.begin(); iter != writer.end(); ++iter )
101  {
102  ( *iter )->save( output );
103  output << std::endl;
104  }
105 
106  output.close();
107 }
108 
110 {
111  save( m_parsers );
112 }
113 
115 {
116  try
117  {
118  // Parse the file
119  wlog::info( "Project File" ) << "Loading project file \"" << m_project.file_string() << "\".";
120 
121  // read the file
122  std::ifstream input( m_project.file_string().c_str() );
123  if( !input.is_open() )
124  {
125  throw WFileNotFound( std::string( "The project file \"" ) + m_project.file_string() +
126  std::string( "\" does not exist." ) );
127  }
128 
129  // the comment
130  static const boost::regex commentRe( "^ *//.*$" );
131 
132  // read it line by line
133  std::string line; // the current line
134  int i = 0; // line counter
135  bool match = false; // true of a parser successfully parsed the line
136  boost::smatch matches; // the list of matches
137 
138  while( std::getline( input, line ) )
139  {
140  ++i; // line number
141  match = false;
142 
143  // allow each parser to handle the line.
144  for( std::vector< boost::shared_ptr< WProjectFileIO > >::const_iterator iter = m_parsers.begin(); iter != m_parsers.end(); ++iter )
145  {
146  try
147  {
148  if( ( *iter )->parse( line, i ) )
149  {
150  match = true;
151  // the first parser matching this line -> next line
152  break;
153  }
154  }
155  catch( const std::exception& e )
156  {
157  wlog::error( "Project Loader" ) << "Line " << i << ": Parsing caused an exception. Line Malformed? Skipping.";
158  }
159  }
160 
161  // did someone match this line? Or is it empty or a comment?
162  if( !match && !line.empty() && !boost::regex_match( line, matches, commentRe ) )
163  {
164  // no it is something else -> warning!
165  wlog::warn( "Project Loader" ) << "Line " << i << ": Malformed. Skipping.";
166  }
167  }
168 
169  input.close();
170 
171  // finally, let every one know that we have finished
172  for( std::vector< boost::shared_ptr< WProjectFileIO > >::const_iterator iter = m_parsers.begin(); iter != m_parsers.end(); ++iter )
173  {
174  ( *iter )->done();
175  }
176  }
177  catch( const std::exception& e )
178  {
179  // remove from thread list
180  WKernel::getRunningKernel()->getRootContainer()->finishedPendingThread( shared_from_this() );
181 
182  // re-throw
183  throw e;
184  }
185 
186  // remove from thread list
187  WKernel::getRunningKernel()->getRootContainer()->finishedPendingThread( shared_from_this() );
188 }
189