xref: /trunk/main/autodoc/source/parser/inc/semantic/callf.hxx (revision cdf0e10c4e3984b49a9502b011690b615761d4a3)
1 /*************************************************************************
2  *
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
5  * Copyright 2000, 2010 Oracle and/or its affiliates.
6  *
7  * OpenOffice.org - a multi-platform office productivity suite
8  *
9  * This file is part of OpenOffice.org.
10  *
11  * OpenOffice.org is free software: you can redistribute it and/or modify
12  * it under the terms of the GNU Lesser General Public License version 3
13  * only, as published by the Free Software Foundation.
14  *
15  * OpenOffice.org 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 version 3 for more details
19  * (a copy is included in the LICENSE file that accompanied this code).
20  *
21  * You should have received a copy of the GNU Lesser General Public License
22  * version 3 along with OpenOffice.org.  If not, see
23  * <http://www.openoffice.org/license.html>
24  * for a copy of the LGPLv3 License.
25  *
26  ************************************************************************/
27 
28 #ifndef ADC_CPP_CALLF_HXX
29 #define ADC_CPP_CALLF_HXX
30 
31 // USED SERVICES
32 
33 
34 
35 
36 /** This represents a function to be called, if a specific kind of token
37     arrives in the semantic parser.
38 
39     @descr This class is only to be used as member of PeStatus<PE>.
40     @template PE
41         The owning ParseEnvironment.
42     @see PeStatus, ParseEnvironment
43 */
44 template <class PE>
45 class CallFunction
46 {
47   public:
48     typedef void (PE::*F_Tok)(const char *);
49 
50                         CallFunction(
51                             F_Tok               i_f2Call,
52                             INT16               i_nTokType );
53 
54     F_Tok               GetF() const;
55     INT16               TokType() const;
56 
57   private:
58     // DATA
59     F_Tok               f2Call;
60     INT16               nTokType;
61 };
62 
63 
64 /** One state within a ParseEnvironment.
65 
66     @template PE
67         The owning ParseEnvironment.
68 */
69 template <class PE>
70 class PeStatus
71 {
72   public:
73     typedef typename CallFunction<PE>::F_Tok  F_Tok;
74 
75                         PeStatus(
76                             PE &                i_rMyPE,
77                             uintt               i_nSize,
78                             F_Tok *             i_pFuncArray,
79                             INT16 *             i_pTokTypeArray,
80                             F_Tok               i_pDefault );
81     virtual             ~PeStatus();
82 
83     virtual void        Call_Handler(
84                             INT16               i_nTokTypeId,
85                             const char *        i_sTokenText ) const;
86 
87   private:
88     bool                CheckForCall(
89                             uintt               i_nPos,
90                             INT16               i_nTokTypeId,
91                             const char *        i_sTokenText ) const;
92 
93     PE *                pMyPE;
94     std::vector< CallFunction<PE> >
95                         aBranches;
96     F_Tok               fDefault;
97 };
98 
99 
100 template <class PE>
101 class PeStatusArray
102 {
103   public:
104     typedef typename PE::E_State    State;
105 
106                         PeStatusArray();
107     void                InsertState(
108                             State               i_ePosition,
109                             DYN PeStatus<PE> &  let_drState );
110                         ~PeStatusArray();
111 
112     const PeStatus<PE> &
113                         operator[](
114                             State               i_ePosition ) const;
115 
116     void                SetCur(
117                             State               i_eCurState );
118     const PeStatus<PE> &
119                         Cur() const;
120 
121   private:
122     DYN PeStatus<PE> *  aStati[PE::size_of_states];
123     State               eState;
124 };
125 
126 
127 
128 // IMPLEMENTATION
129 
130 
131 // CallFunction
132 
133 template <class PE>
134 CallFunction<PE>::CallFunction( F_Tok   i_f2Call,
135                                 INT16   i_nTokType )
136     :   f2Call(i_f2Call),
137         nTokType(i_nTokType)
138 {
139 }
140 
141 template <class PE>
142 inline typename CallFunction<PE>::F_Tok
143 CallFunction<PE>::GetF() const
144 {
145     return f2Call;
146 }
147 
148 template <class PE>
149 inline INT16
150 CallFunction<PE>::TokType() const
151 {
152     return nTokType;
153 }
154 
155 
156 
157 // PeStatus
158 
159 template <class PE>
160 PeStatus<PE>::PeStatus( PE &        i_rMyPE,
161                         uintt       i_nSize,
162                         F_Tok *     i_pFuncArray,
163                         INT16 *     i_pTokTypeArray,
164                         F_Tok       i_fDefault )
165     :   pMyPE(&i_rMyPE),
166         fDefault(i_fDefault)
167 {
168     aBranches.reserve(i_nSize);
169     for ( uintt i = 0; i < i_nSize; ++i )
170     {
171 //      csv_assert(i > 0 ? i_pTokTypeArray[i] > i_pTokTypeArray[i-1] : true);
172         aBranches.push_back( CallFunction<PE>( i_pFuncArray[i], i_pTokTypeArray[i]) );
173     }  // end for
174 }
175 
176 template <class PE>
177 PeStatus<PE>::~PeStatus()
178 {
179 
180 }
181 
182 template <class PE>
183 void
184 PeStatus<PE>::Call_Handler( INT16               i_nTokTypeId,
185                             const char *        i_sTokenText ) const
186 {
187     uintt nSize = aBranches.size();
188     uintt nPos = nSize / 2;
189 
190     if ( i_nTokTypeId < aBranches[nPos].TokType() )
191     {
192         for ( --nPos; intt(nPos) >= 0; --nPos )
193         {
194             if (CheckForCall(nPos, i_nTokTypeId, i_sTokenText))
195                 return;
196         }
197     }
198     else
199     {
200         for ( ; nPos < nSize; ++nPos )
201         {
202             if (CheckForCall(nPos, i_nTokTypeId, i_sTokenText))
203                 return;
204         }
205     }
206 
207     (pMyPE->*fDefault)(i_sTokenText);
208 }
209 
210 template <class PE>
211 bool
212 PeStatus<PE>::CheckForCall( uintt               i_nPos,
213                             INT16               i_nTokTypeId,
214                             const char *        i_sTokenText ) const
215 {
216     if ( aBranches[i_nPos].TokType() == i_nTokTypeId )
217     {
218         (pMyPE->*aBranches[i_nPos].GetF())(i_sTokenText);
219         return true;
220     }
221     return false;
222 }
223 
224 // PeStatusArray
225 
226 template <class PE>
227 PeStatusArray<PE>::PeStatusArray()
228     :   eState(PE::size_of_states)
229 {
230     memset(aStati, 0, sizeof aStati);
231 }
232 
233 template <class PE>
234 void
235 PeStatusArray<PE>::InsertState( State               i_ePosition,
236                                 DYN PeStatus<PE> &  let_drState )
237 {
238     csv_assert(aStati[i_ePosition] == 0);
239     aStati[i_ePosition] = &let_drState;
240 }
241 
242 template <class PE>
243 PeStatusArray<PE>::~PeStatusArray()
244 {
245     int i_max = PE::size_of_states;
246     for (int i = 0; i < i_max; i++)
247     {
248         delete aStati[i];
249     }  // end for
250 }
251 
252 template <class PE>
253 inline const PeStatus<PE> &
254 PeStatusArray<PE>::operator[]( State i_ePosition ) const
255 {
256     csv_assert( uintt(i_ePosition) < PE::size_of_states );
257     csv_assert( aStati[i_ePosition] != 0 );
258     return *aStati[i_ePosition];
259 }
260 
261 template <class PE>
262 inline void
263 PeStatusArray<PE>::SetCur( State i_eCurState )
264 {
265     eState = i_eCurState;
266 }
267 
268 
269 template <class PE>
270 const PeStatus<PE> &
271 PeStatusArray<PE>::Cur() const
272 {
273     return (*this)[eState];
274 }
275 
276 #define SEMPARSE_CREATE_STATUS(penv, state, default_function) \
277     pStati->InsertState( state, \
278                         *new PeStatus<penv>( \
279         *this, \
280         sizeof( stateT_##state ) / sizeof (INT16), \
281         stateF_##state, \
282         stateT_##state, \
283         &penv::default_function ) )
284 
285 
286 #endif
287 
288