]> git.mxchange.org Git - flightgear.git/blob - src/FDM/JSBSim/FGConfigFile.cpp
Syncing with latest JSBSim code with retractable landing gear support.
[flightgear.git] / src / FDM / JSBSim / FGConfigFile.cpp
1 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2
3  Header:       FGConfigFile.h
4  Author:       Jon Berndt
5  Date started: 03/29/00
6  Purpose:      Config file read-in class
7  Called by:    FGAircraft
8
9 FUNCTIONAL DESCRIPTION
10 --------------------------------------------------------------------------------
11
12 HISTORY
13 --------------------------------------------------------------------------------
14 03/16/2000 JSB  Created
15
16 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
17 INCLUDES
18 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
19
20 #include "FGConfigFile.h"
21 #include <stdlib.h>
22 #include <math.h>
23
24 static const char *IdSrc = "$Id$";
25 static const char *IdHdr = ID_CONFIGFILE;
26
27 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
28 CLASS IMPLEMENTATION
29 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
30
31 FGConfigFile::FGConfigFile(string cfgFileName)
32 {
33 #if defined ( sgi ) && !defined( __GNUC__ )
34   cfgfile.open(cfgFileName.c_str(), ios::in );
35 #else
36   cfgfile.open(cfgFileName.c_str(), ios::in | ios::binary );
37 #endif
38   CommentsOn = false;
39   CurrentIndex = 0;
40   Opened = true;
41 #if defined ( sgi ) && !defined( __GNUC__ )
42    if (!cfgfile.fail() && !cfgfile.eof())  GetNextConfigLine();
43 #else
44   if (cfgfile.is_open()) GetNextConfigLine();
45 #endif
46   else Opened = false;
47
48   if (debug_lvl & 2) cout << "Instantiated: FGConfigFile" << endl;
49 }
50
51 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
52
53 FGConfigFile::~FGConfigFile()
54 {
55   cfgfile.close();
56   if (debug_lvl & 2) cout << "Destroyed:    FGConfigFile" << endl;
57 }
58
59 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
60
61 string FGConfigFile::GetNextConfigLine(void)
62 {
63   
64   int comment_starts_at;
65   int comment_ends_at;
66   int comment_length;
67   int line_length;
68   bool start_comment, end_comment;
69   string CommentStringTemp;
70
71   do {
72     CurrentLine = GetLine();
73     line_length = CurrentLine.length();
74     comment_starts_at = CurrentLine.find("<!--");
75     
76     if (comment_starts_at >= 0) start_comment = true;
77     else start_comment = false;
78     
79     comment_ends_at = CurrentLine.find("-->");
80     
81     if (comment_ends_at >= 0) end_comment = true;
82     else end_comment = false;
83
84     if (!start_comment && !end_comment) {                              //  command comment
85       if (CommentsOn) CommentStringTemp = CurrentLine;
86       CommentString += CommentStringTemp + "\r\n";
87     } else if (start_comment && comment_ends_at > comment_starts_at) { //  <!-- ... -->
88       CommentsOn = false;
89       comment_length = comment_ends_at + 2 - comment_starts_at + 1;
90       LineComment = CurrentLine.substr(comment_starts_at+4, comment_length-4-3);
91       CurrentLine.erase(comment_starts_at, comment_length);
92     } else if ( start_comment && !end_comment) {                       //  <!-- ...
93       CommentsOn = true;
94       comment_length = line_length - comment_starts_at;
95       CommentStringTemp = CurrentLine.substr(comment_starts_at+4, comment_length-4);
96       CommentString = CommentStringTemp + "\r\n";
97       CurrentLine.erase(comment_starts_at, comment_length);
98     } else if (!start_comment && end_comment) {                       //  ... -->
99       CommentsOn = false;
100       comment_length = comment_ends_at + 2 + 1;
101       CommentStringTemp = CurrentLine.substr(0, comment_length-4);
102       CommentString += CommentStringTemp + "\r\n";
103       CurrentLine.erase(0, comment_length);
104     } else if (start_comment && comment_ends_at < comment_starts_at) { //  --> command <!--
105       cerr << "Old comment ends and new one starts - bad JSBSim config file form." << endl;
106       CommentsOn = false;
107       comment_length = comment_ends_at + 2 + 1;
108       CommentStringTemp = CurrentLine.substr(0, comment_length-4);
109       CommentString += CommentStringTemp + "\r\n";
110       CurrentLine.erase(0, comment_length);
111     }
112     
113   } while (CommentsOn);
114
115   if (CurrentLine.length() == 0) GetNextConfigLine();
116   CurrentIndex = 0;
117   return CurrentLine;
118 }
119
120 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
121
122 string FGConfigFile::GetValue(string val)
123 {
124   unsigned int pos, p1, p2, ptest;
125
126   if (val == "") {    // this call is to return the tag value
127     pos = CurrentLine.find("<");
128     if (pos != CurrentLine.npos) { // beginning brace found "<"
129       p1 = CurrentLine.find_first_not_of(" ",pos+1);
130       if (p1 != CurrentLine.npos) { // found first character of tag
131         p2 = CurrentLine.find_first_of(" >",p1+1);
132         if (p2 == CurrentLine.npos) p2 = p1+1;
133         return CurrentLine.substr(p1,p2-p1);
134       }
135     } else {   // beginning brace "<" not found; this is a regular data line
136       pos = CurrentLine.find_first_not_of(" ");
137       if (pos != CurrentLine.npos) {  // first character in line found
138         p2 = CurrentLine.find_first_of(" ",pos+1);
139         if (p2 != CurrentLine.npos) {
140           return CurrentLine.substr(pos,p2-pos);
141         } else {
142           return CurrentLine.substr(pos,CurrentLine.length()-pos);
143         }
144       }
145     }
146   } else { // return a value for a specific tag
147     pos = CurrentLine.find(val);
148     if (pos != CurrentLine.npos) {
149       pos = CurrentLine.find("=",pos);
150       if (pos != CurrentLine.npos) {
151         ptest = CurrentLine.find_first_not_of(" ",pos+1);
152         if (ptest != CurrentLine.npos) {
153           p1 = ptest + 1;
154           if (CurrentLine[ptest] == '"') { // quoted
155             p2 = CurrentLine.find_first_of("\"",p1);
156           } else { // not quoted
157             p2 = CurrentLine.find_first_of(" ",p1);
158           }
159           if (p2 != CurrentLine.npos) {
160             return CurrentLine.substr(p1,p2-p1);
161           }
162         }
163       } else {   // "=" not found
164         pos = CurrentLine.find(val);
165         pos = CurrentLine.find_first_of(" ",pos+1);
166         ptest = CurrentLine.find_first_not_of(" ",pos+1);
167         if (ptest != CurrentLine.npos) {
168           if (CurrentLine[ptest] == '"') { // quoted
169             p1 = ptest + 1;
170             p2 = CurrentLine.find_first_of("\"",p1);
171           } else { // not quoted
172             p1 = ptest;
173             p2 = CurrentLine.find_first_of(" ",p1);
174           }
175           if (p2 != CurrentLine.npos) {
176             return CurrentLine.substr(p1,p2-p1);
177           } else {
178             p2 = CurrentLine.length();
179             return CurrentLine.substr(p1,p2-p1);
180           }
181         }
182       }
183     }
184   }
185
186   return string("");
187 }
188
189 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
190
191 string FGConfigFile::GetValue(void)
192 {
193   return GetValue("");
194 }
195
196 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
197
198 string FGConfigFile::GetLine(void)
199 {
200   string scratch = "";
201   int test;
202
203   while ((test = cfgfile.get()) != EOF) {
204     if (test >= 0x20 || test == 0x09) {
205       if (test == 0x09) {
206         scratch += (char)0x20;
207       } else {
208         scratch += (char)test;
209       }
210     } else {
211       if ((test = cfgfile.get()) != EOF) { // get *next* character
212 #if defined ( sgi ) && !defined( __GNUC__ )
213         if (test >= 0x20 || test == 0x09) cfgfile.putback(test);
214 #else
215         if (test >= 0x20 || test == 0x09) cfgfile.unget();
216 #endif
217         break;
218       }
219     }
220   }
221   if (cfgfile.eof()) return string("EOF");
222   return scratch;
223 }
224
225 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
226 /*
227 FGConfigFile& FGConfigFile::operator>>(double& val)
228 {
229   unsigned int pos, end;
230
231   pos = CurrentLine.find_first_not_of(", ",CurrentIndex);
232   if (pos == CurrentLine.npos) pos = CurrentLine.length();
233   end = CurrentLine.find_first_of(", ",pos+1);
234   if (end == CurrentLine.npos) end = CurrentLine.length();
235   string str = CurrentLine.substr(pos, end - pos);
236   val = strtod(str.c_str(),NULL);
237   CurrentIndex = end+1;
238   if (CurrentIndex >= CurrentLine.length()) GetNextConfigLine();
239   return *this;
240 }
241 */
242 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
243
244 FGConfigFile& FGConfigFile::operator>>(double& val)
245 {
246   unsigned int pos, end;
247
248   pos = CurrentLine.find_first_not_of(", ",CurrentIndex);
249   if (pos == CurrentLine.npos) pos = CurrentLine.length();
250   end = CurrentLine.find_first_of(", ",pos+1);
251   if (end == CurrentLine.npos) end = CurrentLine.length();
252   string str = CurrentLine.substr(pos, end - pos);
253   val = strtod(str.c_str(),NULL);
254   CurrentIndex = end+1;
255   if (CurrentIndex >= CurrentLine.length()) GetNextConfigLine();
256   return *this;
257 }
258
259 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
260
261 FGConfigFile& FGConfigFile::operator>>(int& val)
262 {
263   unsigned int pos, end;
264
265   pos = CurrentLine.find_first_not_of(", ",CurrentIndex);
266   if (pos == CurrentLine.npos) pos = CurrentLine.length();
267   end = CurrentLine.find_first_of(", ",pos+1);
268   if (end == CurrentLine.npos) end = CurrentLine.length();
269   string str = CurrentLine.substr(pos, end - pos);
270   val = atoi(str.c_str());
271   CurrentIndex = end+1;
272   if (CurrentIndex >= CurrentLine.length()) GetNextConfigLine();
273   return *this;
274 }
275
276 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
277
278 FGConfigFile& FGConfigFile::operator>>(eParam& val)
279 {
280   unsigned int pos, end;
281
282   pos = CurrentLine.find_first_not_of(", ",CurrentIndex);
283   if (pos == CurrentLine.npos) pos = CurrentLine.length();
284   end = CurrentLine.find_first_of(", ",pos+1);
285   if (end == CurrentLine.npos) end = CurrentLine.length();
286   string str = CurrentLine.substr(pos, end - pos);
287   val = (eParam)atoi(str.c_str());
288   CurrentIndex = end+1;
289   if (CurrentIndex >= CurrentLine.length()) GetNextConfigLine();
290   return *this;
291 }
292
293 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
294
295 FGConfigFile& FGConfigFile::operator>>(string& str)
296 {
297   unsigned int pos, end;
298
299   pos = CurrentLine.find_first_not_of(", ",CurrentIndex);
300   if (pos == CurrentLine.npos) pos = CurrentLine.length();
301   end = CurrentLine.find_first_of(", ",pos+1);
302   if (end == CurrentLine.npos) end = CurrentLine.length();
303   str = CurrentLine.substr(pos, end - pos);
304   CurrentIndex = end+1;
305   if (CurrentIndex >= CurrentLine.length()) GetNextConfigLine();
306   return *this;
307 }
308
309 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
310
311 void FGConfigFile::ResetLineIndexToZero(void)
312 {
313   CurrentIndex = 0;
314 }
315
316 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
317
318 void FGConfigFile::Debug(void)
319 {
320     //TODO: Add your source code here
321 }
322