1 #include "ace/OS_NS_stdlib.h"
2 #include "ace/OS_NS_string.h"
3 #include "ace/FILE_Connector.h"
4 #include "ace/Message_Block.h"
5 #include "ace/Singleton.h"
6 #include "ace/Unbounded_Queue.h"
12 #include "jaws3/Config_File.h"
13 #include "jaws3/Symbol_Table.h"
15 // = Helper class to manage "constant" strings.
23 while (this->queue_
.dequeue_head (p
) != -1)
27 const ACE_TCHAR
* duplicate (const ACE_TCHAR
*s
)
30 const ACE_TCHAR
*d
= 0;
31 ACE_Unbounded_Queue_Iterator
<void *> iter (this->queue_
);
35 d
= (const ACE_TCHAR
*) *x
;
36 if (ACE_OS::strcmp (d
, s
) == 0)
44 d
= ACE_OS::strdup (s
);
45 this->queue_
.enqueue_tail ((void *) d
);
52 ACE_Unbounded_Queue
<void *> queue_
;
56 // = Underlying implementation class.
59 class JAWS_Config_File_Impl
62 JAWS_Config_File_Impl (const ACE_TCHAR
*config_file
);
63 ~JAWS_Config_File_Impl ();
64 int find (const ACE_TCHAR
*key
, const ACE_TCHAR
*&value
);
70 enum { JAWS_CONFIG_FILE_SYMBOL_TABLE_SIZE
= 211 };
74 JAWS_strings
*strings_
;
75 JAWS_Symbol_Table
*symbols_
;
78 JAWS_Config_File_Impl::JAWS_Config_File_Impl (const ACE_TCHAR
*config_file
)
79 : faddr_ (config_file
)
83 this->strings_
= new JAWS_strings
;
84 this->symbols_
= new JAWS_Symbol_Table (JAWS_CONFIG_FILE_SYMBOL_TABLE_SIZE
);
88 JAWS_Config_File_Impl::~JAWS_Config_File_Impl ()
90 delete this->symbols_
;
92 delete this->strings_
;
97 JAWS_Config_File_Impl::find (const ACE_TCHAR
*key
, const ACE_TCHAR
*&value
)
99 return this->symbols_
->find (key
, value
);
103 JAWS_Config_File_Impl::parse_file ()
105 ACE_FILE_Connector fconnector
;
108 if (fconnector
.connect ( fio
117 ACE_Message_Block
buffer (8192);
118 ACE_Message_Block
line (4096);
120 const ACE_TCHAR
*sym_name
;
121 const ACE_TCHAR
*sym_value
;
122 int last_line_was_read
= 0;
123 ACE_TCHAR
*end_of_current_line
= 0;
126 while (last_line_was_read
127 || (count
= fio
.recv (buffer
.wr_ptr (), buffer
.space () - 2)) >= 0)
129 end_of_current_line
= 0;
131 // Make sure input is newline terminated if it is the last line,
132 // and always null terminated.
133 if (! last_line_was_read
)
137 buffer
.wr_ptr (count
);
138 // Scan forward for at least one newline character
139 p
= buffer
.rd_ptr ();
140 while (p
!= buffer
.wr_ptr ())
147 if (p
== buffer
.wr_ptr ())
150 end_of_current_line
= p
;
154 if (buffer
.wr_ptr ()[-1] != '\n')
156 buffer
.wr_ptr ()[0] = '\n';
160 last_line_was_read
= 1;
163 buffer
.wr_ptr ()[0] = '\0';
166 if (end_of_current_line
== 0)
168 end_of_current_line
= buffer
.rd_ptr ();
169 while (*end_of_current_line
!= '\n')
170 end_of_current_line
++;
173 // If buffer is not pointing to a continuation line, or there is
174 // no more input, then can commit the scanned configuration
176 if (line
.length () != 0
177 && ((last_line_was_read
&& buffer
.length () == 0)
178 || (buffer
.rd_ptr ()[0] != ' '
179 && buffer
.rd_ptr ()[0] != '\t')))
182 ACE_TCHAR
*value
= 0;
184 name
= line
.rd_ptr ();
185 for (p
= name
; *p
!= '\0'; p
++)
190 while (p
!= name
&& (p
[-1] == ' ' || p
[-1] == '\t'))
198 value
= line
.rd_ptr ();
199 while (*value
== ' ' || *value
== '\t')
202 while (p
!= value
&& (p
[-1] == ' ' || p
[-1] == '\t'))
206 sym_name
= this->strings_
->duplicate (name
);
207 sym_value
= this->strings_
->duplicate (value
);
208 this->symbols_
->rebind (sym_name
, sym_value
);
214 // If we are done, we are done!
215 if (last_line_was_read
&& buffer
.length () == 0)
218 // If the buffer is pointing at a comment line, ignore it.
219 if (buffer
.rd_ptr ()[0] == '#'
220 || buffer
.rd_ptr ()[0] == '\n'
221 || (buffer
.rd_ptr ()[0] == '\r' && buffer
.rd_ptr ()[1] == '\n'))
223 buffer
.rd_ptr (end_of_current_line
+ 1);
228 // Whatever is left is either the start of a name-value-pair or a
229 // continuation of one.
230 line
.copy (buffer
.rd_ptr (),
231 end_of_current_line
- buffer
.rd_ptr ());
233 while (p
!= line
.rd_ptr () && (p
[-1] == ' ' || p
[-1] == '\t'))
236 line
.wr_ptr ()[0] = '\0';
237 buffer
.rd_ptr (end_of_current_line
+ 1);
245 JAWS_Config_File_Impl::reset ()
247 delete this->symbols_
;
248 delete this->strings_
;
249 this->strings_
= new JAWS_strings
;
250 this->symbols_
= new JAWS_Symbol_Table (JAWS_CONFIG_FILE_SYMBOL_TABLE_SIZE
);
255 JAWS_Config_File_Impl::dump ()
257 JAWS_SYMBOL_TABLE_ITERATOR
iter (*this->symbols_
);
258 JAWS_SYMBOL_TABLE_ENTRY
*entry
= 0;
260 while (iter
.next (entry
))
262 ACE_DEBUG ((LM_DEBUG
, "[%D|%t] %s=%s\n",
269 JAWS_Config_File::JAWS_Config_File (const ACE_TCHAR
*config_file
,
270 const ACE_TCHAR
*config_dir
)
272 ACE_TCHAR filename
[MAXPATHLEN
];
273 ACE_OS::strcpy (filename
, config_dir
);
274 ACE_OS::strcat (filename
, config_file
);
276 this->impl_
= new JAWS_Config_File_Impl (filename
);
280 JAWS_Config_File::find (const ACE_TCHAR
*key
, const ACE_TCHAR
*&value
)
282 return this->impl_
->find (key
, value
);
286 JAWS_Config_File::reset ()
288 this->impl_
->reset ();
292 JAWS_Config_File::dump ()
294 this->impl_
->dump ();