xref: /AOO41X/main/xml2cmp/source/x2cclass/xml_cdff.cxx (revision ab595ff673037ca65571681ab9d2dfec8bce159c)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 #include "xml_cdff.hxx"
25 
26 #include <string.h>
27 #include <tools/stream.hxx>
28 #include "xml_cdim.hxx"
29 #include <ctype.h>
30 
31 
32 typedef ComponentDescriptionImpl::ValueList CdiValueList;
33 
34 class dyn_buffer
35 {
36   public:
dyn_buffer()37                         dyn_buffer()                    : s(0) {}
~dyn_buffer()38                         ~dyn_buffer()                   { if (s) delete [] s; }
operator const char*() const39                         operator const char *() const   { return s; }
operator ->()40     char *              operator->()                    { return s; }
operator [](INT32 ix)41     char &              operator[](
42                             INT32 ix )                  { return s[ix]; }
SetSize(INT32 i_size)43     void                SetSize(
44                             INT32 i_size )              { if (s) delete [] s; s = new char [i_size]; }
45   private:
46     char * s;
47 };
48 
49 
50 inline BOOL
LoadXmlFile(dyn_buffer & o_rBuffer,const UniString & i_sXmlFilePath)51 LoadXmlFile( dyn_buffer &       o_rBuffer,
52              const UniString &  i_sXmlFilePath )
53 {
54     BOOL ret = TRUE;
55     SvFileStream aXmlFile;
56 
57     aXmlFile.Open(i_sXmlFilePath, STREAM_READ);
58     if (aXmlFile.GetErrorCode() != FSYS_ERR_OK)
59         ret = FALSE;
60     if (ret)
61     {
62         aXmlFile.Seek(STREAM_SEEK_TO_END);
63         INT32 nBufferSize = aXmlFile.Tell();
64         o_rBuffer.SetSize(nBufferSize + 1);
65         o_rBuffer[nBufferSize] = '\0';
66         aXmlFile.Seek(0);
67         if (aXmlFile.Read(o_rBuffer.operator->(), nBufferSize) == 0)
68             ret = FALSE;
69     }
70 
71     aXmlFile.Close();
72     return ret;
73 }
74 
75 
76 
CompDescrsFromAnXmlFile()77 CompDescrsFromAnXmlFile::CompDescrsFromAnXmlFile()
78     :   dpDescriptions(new std::vector< ComponentDescriptionImpl* >),
79         eStatus(not_yet_parsed)
80 {
81     dpDescriptions->reserve(3);
82 }
83 
~CompDescrsFromAnXmlFile()84 CompDescrsFromAnXmlFile::~CompDescrsFromAnXmlFile()
85 {
86     Empty();
87     delete dpDescriptions;
88 }
89 
90 
91 BOOL
Parse(const UniString & i_sXmlFilePath)92 CompDescrsFromAnXmlFile::Parse( const UniString & i_sXmlFilePath )
93 {
94     dyn_buffer      dpBuffer;
95 
96     if (! LoadXmlFile(dpBuffer,i_sXmlFilePath) )
97     {
98         eStatus = cant_read_file;
99         return FALSE;
100     }
101 
102     const char *    pTokenStart = 0;
103     const char *    pBufferPosition = dpBuffer;
104     INT32           nTokenLength = 0;
105     BOOL            bWithinElement = FALSE;
106 
107     CdiValueList *  pCurTagData = 0;
108     ByteString      sStatusValue;   // Used only if a <Status ...> tag is found.
109 
110 
111     for ( ComponentDescriptionImpl::ParseUntilStartOfDescription(pBufferPosition);
112           pBufferPosition != 0;
113           ComponentDescriptionImpl::ParseUntilStartOfDescription(pBufferPosition) )
114     {
115         ComponentDescriptionImpl * pCurCD = 0;
116         pCurCD = new ComponentDescriptionImpl;
117         dpDescriptions->push_back(pCurCD);
118 
119         for ( ; *pBufferPosition != '\0' && pCurCD != 0; )
120         {
121             switch (*pBufferPosition)
122             {
123                 case '<' :
124                         if (! bWithinElement)
125                         {
126                             pCurTagData = pCurCD->GetBeginTag(sStatusValue, pBufferPosition);
127                             if (pCurTagData != 0)
128                             {
129                                 if (sStatusValue.Len () == 0)
130                                 {
131                                     // Start new token:
132                                     pTokenStart = pBufferPosition;
133                                     nTokenLength = 0;
134                                     bWithinElement = TRUE;;
135                                 }
136                                 else
137                                 {
138                                     // Status tag is already parsed:
139                                     pCurTagData->push_back(sStatusValue);
140                                 }   // endif (sStatusValue.Length () == 0)
141                             }
142                             else if ( ComponentDescriptionImpl::CheckEndOfDescription(pBufferPosition) )
143                             {
144                                 pBufferPosition += ComponentDescriptionImpl::DescriptionEndTagSize();
145                                 pCurCD = 0;
146                             }
147                             else
148                             {
149                                 eStatus = inconsistent_file;
150                                 return FALSE;
151                             }   // endif (pCurTagData != 0) elseif() else
152                         }
153                         else if ( pCurTagData->MatchesEndTag(pBufferPosition) )
154                         {
155                             // Finish token:
156                             pBufferPosition += pCurTagData->EndTagLength();
157                             bWithinElement = FALSE;
158 
159                                 // Remove leading and trailing spaces:
160                             while ( isspace(*pTokenStart) )
161                             {
162                                pTokenStart++;
163                                nTokenLength--;
164                             }
165                             while ( nTokenLength > 0
166                                     && isspace(pTokenStart[nTokenLength-1]) )
167                             {
168                                 nTokenLength--;
169                             }
170                                 // Add token to tag values list.
171                             pCurTagData->push_back(ByteString(pTokenStart,nTokenLength));
172                         }
173                         else
174                         {
175                             nTokenLength++;
176                             ++pBufferPosition;
177                         }   // endif (!bWithinElement) else if () else
178                        break;
179                 default:
180                         if (bWithinElement)
181                         {
182                             ++nTokenLength;
183                         }
184                         ++pBufferPosition;
185             }   // end switch
186         }   // end for
187 
188         if (bWithinElement)
189         {
190             eStatus = inconsistent_file;
191             return FALSE;
192         }
193     } // end for
194 
195     return TRUE;
196 }
197 
198 INT32
NrOfDescriptions() const199 CompDescrsFromAnXmlFile::NrOfDescriptions() const
200 {
201     return dpDescriptions->size();
202 }
203 
204 const ComponentDescription &
operator [](INT32 i_nIndex) const205 CompDescrsFromAnXmlFile::operator[](INT32 i_nIndex) const
206 {
207     static const ComponentDescriptionImpl aNullDescr_;
208     return 0 <= i_nIndex && i_nIndex < dpDescriptions->size()
209                 ?   *(*dpDescriptions)[i_nIndex]
210                 :   aNullDescr_;
211 }
212 
213 void
Empty()214 CompDescrsFromAnXmlFile::Empty()
215 {
216     for ( std::vector< ComponentDescriptionImpl* >::iterator aIter = dpDescriptions->begin();
217           aIter != dpDescriptions->end();
218           ++aIter )
219     {
220         delete *aIter;
221     }
222     dpDescriptions->erase( dpDescriptions->begin(),
223                            dpDescriptions->end() );
224 }
225 
226 
227 
228