Home > m > helper > ltpda_xmlread.m

ltpda_xmlread

PURPOSE ^

LTPDA_XMLREAD Reads a XML object

SYNOPSIS ^

function values = ltpda_xmlread(node, obj_name)

DESCRIPTION ^

 LTPDA_XMLREAD Reads a XML object

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

 DESCRIPTION:   LTPDA_XMLREAD Reads a XML object.

 CALL:          obj = ltpda_xmlread(node);
                obj = ltpda_xmlread(node ,'class');
                obj = ltpda_xmlread(node ,'ao');
                obj = ltpda_xmlread(node ,'time');

 XML HIERARCHY: ----------------------   ltpda_object   ----------------------

                <ltpda_object>

                   --> <object> ...
                   --> <cell>   ...

                </ltpda_object>

                -------------------------   object   -------------------------

                <object> ('type' - attribute)

                   <property> ...

                </object>

                ------------------------   property   ------------------------
                --------------------------   cell   --------------------------

                <property> ('type', 'prop_name' -attributes)
            OR  <cell>     ('type'              -attribute)

                   --> atomic element
                         - empty cell
                         - empty double
                         - empty char
                         - char
                         - double
                         - logical
                         - java (necessary for timezone)
                   --> <cell>      ...
                   --> <object>    ...
                   --> <real_data> ...
                       <imag_data> ...

                </property>
            OR  </cell>

                -------   real_data   --------|--------   imag_data   --------
                                              |
                <real_data>('type'-attribute) | <imag_data> ('type' -attribute)
                           ('shape'-attribute)|             ('shape'-attribute)
                                              |
                   --> <matrix> ...           |    --> <matrix> ...
                   --> <vector> ...           |    --> <vector> ...
                                              |
                </real_data>                  | </imag_data>
                                              |
                ---------   matrix   --------------------   vector   ---------
                                              |
                <matrix> ('type' -attribute)  | <vector> ('type' -attribute)
                                              |
                   row vector (double)        |    column vector (double)
                                              |
                </matrix>                     | </vector>

 SYMBOLS:       --> Marks a choice between alternatives.
                ... Indicate that an element may be repeated.

 VERSION:       $Id: ltpda_xmlread.html,v 1.7 2008/03/31 10:27:31 hewitson Exp $

 HISTORY:       31-01-2008 Diepholz
                   Creation

 SEE ALSO:      ltpda_xmlwrite, ltpda_xmlread, ltpda_saveobj

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

CROSS-REFERENCE INFORMATION ^

This function calls: This function is called by:

SUBFUNCTIONS ^

SOURCE CODE ^

0001 % LTPDA_XMLREAD Reads a XML object
0002 %
0003 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0004 %
0005 % DESCRIPTION:   LTPDA_XMLREAD Reads a XML object.
0006 %
0007 % CALL:          obj = ltpda_xmlread(node);
0008 %                obj = ltpda_xmlread(node ,'class');
0009 %                obj = ltpda_xmlread(node ,'ao');
0010 %                obj = ltpda_xmlread(node ,'time');
0011 %
0012 % XML HIERARCHY: ----------------------   ltpda_object   ----------------------
0013 %
0014 %                <ltpda_object>
0015 %
0016 %                   --> <object> ...
0017 %                   --> <cell>   ...
0018 %
0019 %                </ltpda_object>
0020 %
0021 %                -------------------------   object   -------------------------
0022 %
0023 %                <object> ('type' - attribute)
0024 %
0025 %                   <property> ...
0026 %
0027 %                </object>
0028 %
0029 %                ------------------------   property   ------------------------
0030 %                --------------------------   cell   --------------------------
0031 %
0032 %                <property> ('type', 'prop_name' -attributes)
0033 %            OR  <cell>     ('type'              -attribute)
0034 %
0035 %                   --> atomic element
0036 %                         - empty cell
0037 %                         - empty double
0038 %                         - empty char
0039 %                         - char
0040 %                         - double
0041 %                         - logical
0042 %                         - java (necessary for timezone)
0043 %                   --> <cell>      ...
0044 %                   --> <object>    ...
0045 %                   --> <real_data> ...
0046 %                       <imag_data> ...
0047 %
0048 %                </property>
0049 %            OR  </cell>
0050 %
0051 %                -------   real_data   --------|--------   imag_data   --------
0052 %                                              |
0053 %                <real_data>('type'-attribute) | <imag_data> ('type' -attribute)
0054 %                           ('shape'-attribute)|             ('shape'-attribute)
0055 %                                              |
0056 %                   --> <matrix> ...           |    --> <matrix> ...
0057 %                   --> <vector> ...           |    --> <vector> ...
0058 %                                              |
0059 %                </real_data>                  | </imag_data>
0060 %                                              |
0061 %                ---------   matrix   --------------------   vector   ---------
0062 %                                              |
0063 %                <matrix> ('type' -attribute)  | <vector> ('type' -attribute)
0064 %                                              |
0065 %                   row vector (double)        |    column vector (double)
0066 %                                              |
0067 %                </matrix>                     | </vector>
0068 %
0069 % SYMBOLS:       --> Marks a choice between alternatives.
0070 %                ... Indicate that an element may be repeated.
0071 %
0072 % VERSION:       $Id: ltpda_xmlread.html,v 1.7 2008/03/31 10:27:31 hewitson Exp $
0073 %
0074 % HISTORY:       31-01-2008 Diepholz
0075 %                   Creation
0076 %
0077 % SEE ALSO:      ltpda_xmlwrite, ltpda_xmlread, ltpda_saveobj
0078 %
0079 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0080 function values = ltpda_xmlread(node, obj_name)
0081 
0082   if nargin == 1
0083     node_name = char(node.getNodeName);
0084 
0085     switch node_name
0086       case 'ltpda_object'
0087         values = xml_read_ltpda_object(node);
0088       case 'object'
0089         values = xml_read_object(node);
0090       case 'property'
0091         values = xml_read_property_cell(node);
0092       case 'cell'
0093         values = xml_read_property_cell(node);
0094       case 'real_data'
0095         values = xml_read_real_imag_data(node);
0096       case 'imag_data'
0097         values = xml_read_real_imag_data(node);
0098       case 'matrix'
0099         %% row vector
0100         values = sscanf(char(child_node.getTextContent), '%g ', [1,inf]);
0101       case 'vector'
0102         %% column vector
0103         values = sscanf(char(child_node.getTextContent), '%g ');
0104       otherwise
0105         %% Search for the next valid node name.
0106         for ii = 1:node.getLength
0107           item = node.item(ii-1);
0108           if item.hasChildNodes
0109             values = ltpda_xmlread(item);
0110           end
0111         end
0112     end
0113   elseif nargin == 2
0114 
0115     values = [];
0116 
0117     query_node = node.getElementsByTagName('ltpda_object');
0118 
0119     for ii= 1:query_node.getLength
0120 
0121       node = query_node.item(ii-1);
0122 
0123       for jj = 1:node.getLength
0124 
0125         child_node = node.item(jj-1);
0126 
0127         if child_node.hasChildNodes
0128 
0129           % Get node name
0130           node_name = char(child_node.getNodeName);
0131 
0132           switch node_name
0133             case 'object'
0134               val =  xml_read_object(child_node);
0135               if strcmp(class(val), obj_name)
0136                 values = [val values];
0137               else
0138                 warning('### Skip the read object because it is from the class [%s] and not from the class [%s]', class(val), obj_name);
0139               end
0140             otherwise
0141           end
0142         end
0143 
0144       end % over all childs
0145 
0146     end % over all 'ltpda_objects'
0147 
0148   else
0149     error('### Invalid command of this function');
0150   end
0151 end
0152 
0153 
0154 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0155 %
0156 % DESCRIPTION: XML_READ_LTPDA_OBJECT Reads a ltoda_object element with the form:
0157 %
0158 %              <ltpda_object>
0159 %
0160 %                 --> <object> ...
0161 %                 --> <cell>   ...
0162 %
0163 %              </ltpda_object>
0164 %
0165 % SYMBOLS:     --> Marks a choice between alternatives.
0166 %              ... Indicate that an element may be repeated.
0167 %
0168 % HISTORY:     31-01-2008 Diepholz
0169 %                 Creation
0170 %
0171 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0172 function values = xml_read_ltpda_object(node)
0173 
0174   values = [];
0175 
0176   for ii = 1:node.getLength
0177 
0178     child_node = node.item(ii-1);
0179 
0180     if child_node.hasChildNodes
0181 
0182       % Get Node name
0183       node_name = char(child_node.getNodeName);
0184       switch node_name
0185 
0186         case 'object'
0187           values = [values xml_read_object(child_node)];
0188 
0189         case 'cell'
0190           values{end+1} = xml_read_property_cell(child_node);
0191 
0192         otherwise
0193           error('### The ''ltpda_object'' element can not contain a [%s] element.', node_name);
0194       end
0195     end
0196   end
0197 end
0198 
0199 
0200 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0201 %
0202 % DESCRIPTION: XML_READ_OBJECT Reads a object element with the form:
0203 %
0204 %              <object> ('type' - attribute)
0205 %
0206 %                 <property> ...
0207 %
0208 %              </object>
0209 %
0210 % SYMBOLS:     ... Indicate that an element may be repeated.
0211 %
0212 % HISTORY:     31-01-2008 Diepholz
0213 %                 Creation
0214 %
0215 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0216 function obj = xml_read_object(node)
0217 
0218   obj_type = char(node.getAttribute('type'));
0219   obj = feval(obj_type);
0220 
0221   for ii = 1:node.getLength
0222 
0223     child_node = node.item(ii-1);
0224 
0225     %%% Read only the property if the node is a ELEMENT_NODE.
0226     if child_node.getNodeType == child_node.ELEMENT_NODE
0227 
0228       % Get node name
0229       node_name = char(child_node.getNodeName);
0230       % get property name from the attribute 'prop_name'
0231       prop_name = char(child_node.getAttribute('prop_name'));
0232       switch node_name
0233         case 'property'
0234           prop_value = xml_read_property_cell(child_node);
0235 
0236           %% Set the property value to the object.
0237 
0238           %% If the object is an analysis object the use the setnh function
0239           %% to set the property. Then is guaranteed that no history is added.
0240 %           if strcmp(obj_type, 'ao')
0241 %             obj.(prop_name) = setnh(obj, prop_name, prop_value);
0242 %           else
0243             try
0244               obj.(prop_name) = prop_value;
0245             catch
0246               warning('\n\n### Skip the unknown property [%s] in the object [%s]\n', prop_name, class(obj));
0247               disp([char(10) 'Code me up to convert me into the new structure !!!' char(10) ]);
0248             end
0249 %           end
0250 
0251         otherwise
0252           error('### The ''object'' element can not contain a [%s] element.', node_name);
0253       end
0254     end
0255   end
0256 end
0257 
0258 
0259 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0260 %
0261 % DESCRIPTION: XML_READ_PROPERTY_CELL Reads a property element or a cell element
0262 %              with the form:
0263 %
0264 %              <property> ('type', 'prop_name' -attributes)
0265 % OR:          <cell>     ('type'              -attribute)
0266 %
0267 %                 --> atomic element
0268 %                       - empty cell
0269 %                       - empty double
0270 %                       - empty char
0271 %                       - char
0272 %                       - double
0273 %                       - logical
0274 %                       - java (necessary for timezone)
0275 %                 --> <cell>      ...
0276 %                 --> <object>    ...
0277 %                 --> <real_data> ...
0278 %                     <imag_data> ...
0279 %
0280 %              </property>
0281 % OR:          </cell>
0282 %
0283 % SYMBOLS:     --> Marks a choice between alternatives.
0284 %              ... Indicate that an element may be repeated.
0285 %
0286 % HISTORY:     31-01-2008 Diepholz
0287 %                 Creation
0288 %
0289 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0290 function prop_value = xml_read_property_cell(node)
0291 
0292   prop_value = [];
0293   real_value = [];
0294   imag_value = [];
0295   shape      = [];
0296 
0297   %% Is the length of the node is equal 1 or zero
0298   %% then is the property a atomic element
0299   if node.getLength == 0 || node.getLength == 1
0300     prop_value = xml_read_atomic_element(node);
0301     return
0302   end
0303 
0304   for ii = 1:node.getLength
0305 
0306     child_node = node.item(ii-1);
0307 
0308     if child_node.getNodeType == child_node.ELEMENT_NODE
0309 
0310       %% Get the node name
0311       node_name = char(child_node.getNodeName);
0312 
0313       switch node_name
0314         case 'cell'
0315           shape = getShape(node);
0316           prop_value{end+1} = xml_read_property_cell(child_node);
0317         case 'object'
0318           shape = getShape(child_node);
0319           prop_value = [prop_value xml_read_object(child_node)];
0320         case 'real_data'
0321           real_value = xml_read_real_imag_data(child_node);
0322         case 'imag_data'
0323           imag_value = xml_read_real_imag_data(child_node);
0324         otherwise
0325           error('### The ''property'' or ''cell'' element can not contain a [%s] element.', node_name);
0326       end
0327 
0328       %% Is real_value and imag_value filled then return the complex value
0329       if ~isempty(real_value) && ~isempty(imag_value)
0330         prop_value = complex(real_value, imag_value);
0331       %% Is real_value filled then return the read value
0332       elseif ~isempty(real_value)
0333         prop_value = real_value;
0334       end
0335     end
0336   end
0337 
0338   %% Reshape the prop_value if necessary
0339   if ~isempty(shape)
0340     prop_value = reshape(prop_value, shape);
0341   end
0342 
0343 end
0344 
0345 
0346 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0347 %
0348 % DESCRIPTION: XML_READ_REAL_IMAG_DATA Reads a real_data element or a
0349 %              imag_data element with the form:
0350 %
0351 %              <real_data> ('type' -attribute) <imag_data> ('type' -attribute)
0352 %                          ('shape'-attribute)             ('shape'-attribute)
0353 %
0354 %                 --> <matrix> ...                --> <matrix> ...
0355 %                 --> <vector> ...                --> <vector> ...
0356 %
0357 %              </real_data>                    </imag_data>
0358 %
0359 %              <matrix> ('type' -attribute)    <vector> ('type' -attribute)
0360 %
0361 %                 row vector (double)             column vector (double)
0362 %
0363 %              </matrix>                       </vector>
0364 %
0365 % SYMBOLS:     --> Marks a choice between alternatives.
0366 %              ... Indicate that an element may be repeated.
0367 %
0368 % REMARK:      The matrix elements will be read as a row vector.
0369 %              The vector elements will be read as a column vector.
0370 %
0371 % HISTORY:     31-01-2008 Diepholz
0372 %                 Creation
0373 %
0374 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0375 function value = xml_read_real_imag_data(node)
0376 
0377   value            = [];
0378   header_displayed = true;
0379 
0380   %%% Get the shape of the matrix/vector
0381   shape = getShape(node);
0382 
0383   for ii = 1:node.getLength
0384 
0385     child_node = node.item(ii-1);
0386 
0387     if child_node.hasChildNodes
0388 
0389       %% Get node name
0390       node_name = char(child_node.getNodeName);
0391 
0392       %% Get type
0393       node_type = char(child_node.getAttribute('type'));
0394 
0395       switch node_name
0396         case 'matrix'
0397           %% row vector
0398           if strcmp(node_type, 'sym')
0399             matrix_row = sym(char(child_node.getTextContent));
0400           else
0401             matrix_row = sscanf(char(child_node.getTextContent), '%g ', [1,inf]);
0402           end
0403           value = [value; matrix_row];
0404         case 'vector'
0405           %% column vector
0406           if strcmp(node_type, 'sym')
0407             vector_column = sym(char(child_node.getTextContent));
0408           else
0409             vector_column = sscanf(char(child_node.getTextContent), '%g ');
0410           end
0411           value = [value; vector_column];
0412           header_displayed = TerminalOutput(node, header_displayed, node_name, length(value));
0413         otherwise
0414           error('### The ''real_data'' or ''imag_data'' element can not contain a [%s] element.', node_name);
0415       end
0416     end
0417   end
0418 
0419   if strcmp(node_name, 'matrix')
0420     header_displayed = true;
0421     TerminalOutput(node, header_displayed, node_name, size(value,1));
0422   end
0423   value = reshape(value, shape);
0424 
0425 end
0426 
0427 
0428 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0429 %
0430 % DESCRIPTION: xml_read_atomic_element Reads a atomic element.
0431 %              This function identify the following types:
0432 %                 --> atomic element
0433 %                       - empty cell
0434 %                       - empty double
0435 %                       - empty char
0436 %                       - char
0437 %                       - double
0438 %                       - logical
0439 %                       - java (necessary for timezone)
0440 %
0441 % HISTORY:     31-01-2008 Diepholz
0442 %                 Creation
0443 %
0444 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0445 function values = xml_read_atomic_element(node)
0446 
0447   values = '';
0448 
0449   type = char(node.getAttribute('type'));
0450   switch type
0451     case {'', 'char'}
0452       values = char(node.getTextContent);
0453 
0454       %% Special case if 'values' is empty because
0455       %% there are more than an one empty char fields.
0456       %% For example: '' AND char('', '') AND char('', '', '') AND ...
0457       if isempty(values)
0458         shape = getShape(node);
0459         if any(shape)
0460           char_str = 'char(';
0461           for ii = 1:max(shape)
0462             char_str = [char_str, ''''', '];
0463           end
0464           char_str = char_str(1:end-2);
0465           cmd = strcat('values = ', char_str, ');');
0466           eval(cmd);
0467         else
0468           values = '';
0469         end
0470       end
0471 
0472     case 'double'
0473       number = char(node.getTextContent);
0474 
0475       %% Special case if 'values' is empty because
0476       %% there are more than an one empty double fields.
0477       %% For example: [] AND zeros(1,0) AND zeros(0,1) AND zeros(2,0) AND ...
0478       if isempty(number)
0479         shape = getShape(node);
0480         values = zeros(shape);
0481       else
0482         values = str2double(number);
0483       end
0484 
0485     case 'sym'
0486       number = char(node.getTextContent);
0487 
0488       %% Special case if 'values' is empty because
0489       %% there are more than an one empty double fields.
0490       %% For example: [] AND zeros(1,0) AND zeros(0,1) AND zeros(2,0) AND ...
0491       if isempty(number)
0492         shape = getShape(node);
0493         values = sym(shape);
0494       else
0495         values = sym(number);
0496       end
0497 
0498     case 'cell'
0499       cell_str = char(node.getTextContent);
0500 
0501       %% Special case if 'values' is empty because
0502       %% there are more than an one empty cell fields.
0503       %% For example: {} AND cell(1,0) AND cell(0,1) AND cell(2,0) AND ...
0504       if isempty(cell_str)
0505         shape = getShape(node);
0506         values = cell(shape);
0507       else
0508         error('### Should not happen because a not empty ''cell'' node have several child nodes.');
0509       end
0510 
0511     case 'logical'
0512       if strcmp (char(node.getTextContent), 'true')
0513         values = true;
0514       else
0515         values = false;
0516       end
0517 
0518     case 'sun.util.calendar.ZoneInfo'
0519       values = java.util.TimeZone.getTimeZone(char(node.getTextContent));
0520     otherwise
0521       error('### Unknown type attribute [%s].', type');
0522   end
0523 end
0524 
0525 
0526 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0527 %
0528 % DESCRIPTION: getShape Helper function to get the shape from the
0529 %              attribute 'shape' as a set of double.
0530 %
0531 % HISTORY:     31-01-2008 Diepholz
0532 %                 Creation
0533 %
0534 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0535 function shape = getShape(node)
0536   shape = [NaN NaN];
0537   if node.hasAttribute('shape')
0538     shape_str = char(node.getAttribute('shape'));
0539     x_idx     = strfind(shape_str, 'x');
0540     shape     = [str2double(shape_str(1:x_idx-1)) str2double(shape_str(x_idx+1:end))];
0541   end
0542 end
0543 
0544 
0545 
0546 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0547 %
0548 % DESCRIPTION: Displays the terminal output.
0549 %
0550 % HISTORY:     31-01-2008 Diepholz
0551 %                 Creation
0552 %
0553 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
0554 function header_displayed = TerminalOutput(node, header_displayed, node_name, number)
0555 
0556   THRESHOLD_DISP_MATRIX = 10;
0557   THRESHOLD_DISP_VECTOR = 1000;
0558 
0559   showing = false;
0560 
0561   if strcmp(node_name, 'matrix')
0562     if number >= THRESHOLD_DISP_MATRIX
0563       showing = true;
0564       add_text = 'matrix lines';
0565     end
0566   else
0567     if number >= THRESHOLD_DISP_VECTOR
0568       showing = true;
0569       add_text = 'data samples';
0570     end
0571   end
0572 
0573   if showing == true
0574 
0575     parent = node.getParentNode; % The parent node have the 'property name' information
0576 
0577     if header_displayed == true
0578       if parent.hasAttribute('prop_name')
0579         disp_prop_name = char(parent.getAttribute('prop_name'));
0580       else
0581         disp_prop_name = 'Unknown Property Name';
0582       end
0583       disp (sprintf('\n%%%%%%%%%%   Read property [%s]   %%%%%%%%%%', disp_prop_name));
0584 
0585       if strcmp(char(node.getNodeName), 'real_data')
0586         disp('%%%%%   real data        %%%%%')
0587       else
0588         disp('%%%%%   imaginary data   %%%%%')
0589       end
0590       header_displayed = false;
0591     end
0592 
0593     disp(sprintf('Read [%d] %s',number, add_text));
0594   end
0595 end
0596 
0597 
0598 
0599 
0600

Generated on Mon 31-Mar-2008 12:20:24 by m2html © 2003