OSDN Git Service

Compiler warnings removal Numerous tweaks to remove compiler warnings where solution...
[tortoisegit/TortoiseGitJp.git] / ext / scintilla / src / LexGAP.cxx
1 // Scintilla source code edit control\r
2 /** @file LexGAP.cxx\r
3  ** Lexer for the GAP language. (The GAP System for Computational Discrete Algebra)\r
4  ** http://www.gap-system.org\r
5  **/\r
6 // Copyright 2007 by Istvan Szollosi ( szteven <at> gmail <dot> com )\r
7 // The License.txt file describes the conditions under which this software may be distributed.\r
8 \r
9 #include <stdlib.h>\r
10 #include <string.h>\r
11 #include <ctype.h>\r
12 #include <stdio.h>\r
13 #include <stdarg.h>\r
14 \r
15 #include "Platform.h"\r
16 \r
17 #include "PropSet.h"\r
18 #include "Accessor.h"\r
19 #include "StyleContext.h"\r
20 #include "KeyWords.h"\r
21 #include "Scintilla.h"\r
22 #include "SciLexer.h"\r
23 \r
24 #ifdef SCI_NAMESPACE\r
25 using namespace Scintilla;\r
26 #endif\r
27 \r
28 static inline bool IsGAPOperator(char ch) {\r
29         if (isalnum(ch)) return false;\r
30         if (ch == '+' || ch == '-' || ch == '*' || ch == '/' ||\r
31                 ch == '^' || ch == ',' || ch == '!' || ch == '.' ||\r
32                 ch == '=' || ch == '<' || ch == '>' || ch == '(' ||\r
33                 ch == ')' || ch == ';' || ch == '[' || ch == ']' ||\r
34                 ch == '{' || ch == '}' || ch == ':' )\r
35                 return true;\r
36         return false;\r
37 }\r
38 \r
39 static void GetRange(unsigned int start, unsigned int end, Accessor &styler, char *s, unsigned int len) {\r
40         unsigned int i = 0;\r
41         while ((i < end - start + 1) && (i < len-1)) {\r
42                 s[i] = static_cast<char>(styler[start + i]);\r
43                 i++;\r
44         }\r
45         s[i] = '\0';\r
46 }\r
47 \r
48 static void ColouriseGAPDoc(unsigned int startPos, int length, int initStyle, WordList *keywordlists[], Accessor &styler) {\r
49 \r
50         WordList &keywords1 = *keywordlists[0];\r
51         WordList &keywords2 = *keywordlists[1];\r
52         WordList &keywords3 = *keywordlists[2];\r
53         WordList &keywords4 = *keywordlists[3];\r
54 \r
55         // Do not leak onto next line\r
56         if (initStyle == SCE_GAP_STRINGEOL) initStyle = SCE_GAP_DEFAULT;\r
57 \r
58         StyleContext sc(startPos, length, initStyle, styler);\r
59 \r
60         for (; sc.More(); sc.Forward()) {\r
61 \r
62                 // Prevent SCE_GAP_STRINGEOL from leaking back to previous line\r
63                 if ( sc.atLineStart ) {\r
64                         if (sc.state == SCE_GAP_STRING) sc.SetState(SCE_GAP_STRING);\r
65                         if (sc.state == SCE_GAP_CHAR) sc.SetState(SCE_GAP_CHAR);\r
66                 }\r
67 \r
68                 // Handle line continuation generically\r
69                 if (sc.ch == '\\' ) {\r
70                         if (sc.chNext == '\n' || sc.chNext == '\r') {\r
71                                 sc.Forward();\r
72                                 if (sc.ch == '\r' && sc.chNext == '\n') {\r
73                                         sc.Forward();\r
74                                 }\r
75                                 continue;\r
76                         }\r
77                 }\r
78 \r
79                 // Determine if the current state should terminate\r
80                 switch (sc.state) {\r
81                         case SCE_GAP_OPERATOR :\r
82                                 sc.SetState(SCE_GAP_DEFAULT);\r
83                                 break;\r
84 \r
85                         case SCE_GAP_NUMBER :\r
86                                 if (!IsADigit(sc.ch)) {\r
87                                         if (sc.ch == '\\') {\r
88                                                 if (!sc.atLineEnd) {\r
89                                                         if (!IsADigit(sc.chNext)) {\r
90                                                                 sc.Forward();\r
91                                                                 sc.ChangeState(SCE_GAP_IDENTIFIER);\r
92                                                         }\r
93                                                 }\r
94                                         } else if (isalpha(sc.ch) || sc.ch == '_') {\r
95                                                 sc.ChangeState(SCE_GAP_IDENTIFIER);\r
96                                         }\r
97                                         else sc.SetState(SCE_GAP_DEFAULT);\r
98                                 }\r
99                                 break;\r
100 \r
101                         case SCE_GAP_IDENTIFIER :\r
102                                 if (!(iswordstart(static_cast<char>(sc.ch)) || sc.ch == '$')) {\r
103                                         if (sc.ch == '\\') sc.Forward();\r
104                                         else {\r
105                                                 char s[1000];\r
106                                                 sc.GetCurrent(s, sizeof(s));\r
107                                                 if (keywords1.InList(s)) {\r
108                                                         sc.ChangeState(SCE_GAP_KEYWORD);\r
109                                                 } else if (keywords2.InList(s)) {\r
110                                                         sc.ChangeState(SCE_GAP_KEYWORD2);\r
111                                                 } else if (keywords3.InList(s)) {\r
112                                                         sc.ChangeState(SCE_GAP_KEYWORD3);\r
113                                                 } else if (keywords4.InList(s)) {\r
114                                                         sc.ChangeState(SCE_GAP_KEYWORD4);\r
115                                                 }\r
116                                                 sc.SetState(SCE_GAP_DEFAULT);\r
117                                         }\r
118                                 }\r
119                                 break;\r
120 \r
121                         case SCE_GAP_COMMENT :\r
122                                 if (sc.atLineEnd) {\r
123                                         sc.SetState(SCE_GAP_DEFAULT);\r
124                                 }\r
125                                 break;\r
126 \r
127                         case SCE_GAP_STRING:\r
128                                 if (sc.atLineEnd) {\r
129                                         sc.ChangeState(SCE_GAP_STRINGEOL);\r
130                                 } else if (sc.ch == '\\') {\r
131                                         if (sc.chNext == '\"' || sc.chNext == '\'' || sc.chNext == '\\') {\r
132                                                 sc.Forward();\r
133                                         }\r
134                                 } else if (sc.ch == '\"') {\r
135                                         sc.ForwardSetState(SCE_GAP_DEFAULT);\r
136                                 }\r
137                                 break;\r
138 \r
139                         case SCE_GAP_CHAR:\r
140                                 if (sc.atLineEnd) {\r
141                                         sc.ChangeState(SCE_GAP_STRINGEOL);\r
142                                 } else if (sc.ch == '\\') {\r
143                                         if (sc.chNext == '\"' || sc.chNext == '\'' || sc.chNext == '\\') {\r
144                                                 sc.Forward();\r
145                                         }\r
146                                 } else if (sc.ch == '\'') {\r
147                                         sc.ForwardSetState(SCE_GAP_DEFAULT);\r
148                                 }\r
149                                 break;\r
150 \r
151                         case SCE_GAP_STRINGEOL:\r
152                                 if (sc.atLineStart) {\r
153                                         sc.SetState(SCE_GAP_DEFAULT);\r
154                                 }\r
155                                 break;\r
156                 }\r
157 \r
158                 // Determine if a new state should be entered\r
159                 if (sc.state == SCE_GAP_DEFAULT) {\r
160                         if (IsGAPOperator(static_cast<char>(sc.ch))) {\r
161                                 sc.SetState(SCE_GAP_OPERATOR);\r
162                         }\r
163                         else if (IsADigit(sc.ch)) {\r
164                                 sc.SetState(SCE_GAP_NUMBER);\r
165                         } else if (isalpha(sc.ch) || sc.ch == '_' || sc.ch == '\\' || sc.ch == '$' || sc.ch == '~') {\r
166                                 sc.SetState(SCE_GAP_IDENTIFIER);\r
167                                 if (sc.ch == '\\') sc.Forward();\r
168                         } else if (sc.ch == '#') {\r
169                                 sc.SetState(SCE_GAP_COMMENT);\r
170                         } else if (sc.ch == '\"') {\r
171                                 sc.SetState(SCE_GAP_STRING);\r
172                         } else if (sc.ch == '\'') {\r
173                                 sc.SetState(SCE_GAP_CHAR);\r
174                         }\r
175                 }\r
176 \r
177         }\r
178         sc.Complete();\r
179 }\r
180 \r
181 static int ClassifyFoldPointGAP(const char* s) {\r
182         int level = 0;\r
183         if (strcmp(s, "function") == 0 ||\r
184                 strcmp(s, "do") == 0 ||\r
185                 strcmp(s, "if") == 0 ||\r
186                 strcmp(s, "repeat") == 0 ) {\r
187                 level = 1;\r
188         } else if (strcmp(s, "end") == 0 ||\r
189                         strcmp(s, "od") == 0 ||\r
190                         strcmp(s, "fi") == 0 ||\r
191                         strcmp(s, "until") == 0 ) {\r
192                 level = -1;\r
193         }\r
194         return level;\r
195 }\r
196 \r
197 static void FoldGAPDoc( unsigned int startPos, int length, int initStyle,   WordList** , Accessor &styler) {\r
198         unsigned int endPos = startPos + length;\r
199         int visibleChars = 0;\r
200         int lineCurrent = styler.GetLine(startPos);\r
201         int levelPrev = styler.LevelAt(lineCurrent) & SC_FOLDLEVELNUMBERMASK;\r
202         int levelCurrent = levelPrev;\r
203         char chNext = styler[startPos];\r
204         int styleNext = styler.StyleAt(startPos);\r
205         int style = initStyle;\r
206 \r
207         int lastStart = 0;\r
208 \r
209         for (unsigned int i = startPos; i < endPos; i++) {\r
210                 char ch = chNext;\r
211                 chNext = styler.SafeGetCharAt(i + 1);\r
212                 int stylePrev = style;\r
213                 style = styleNext;\r
214                 styleNext = styler.StyleAt(i + 1);\r
215                 bool atEOL = (ch == '\r' && chNext != '\n') || (ch == '\n');\r
216 \r
217                 if (stylePrev != SCE_GAP_KEYWORD && style == SCE_GAP_KEYWORD) {\r
218                         // Store last word start point.\r
219                         lastStart = i;\r
220                 }\r
221 \r
222                 if (stylePrev == SCE_GAP_KEYWORD) {\r
223                         if(iswordchar(ch) && !iswordchar(chNext)) {\r
224                                 char s[100];\r
225                                 GetRange(lastStart, i, styler, s, sizeof(s));\r
226                                 levelCurrent += ClassifyFoldPointGAP(s);\r
227                         }\r
228                 }\r
229 \r
230                 if (atEOL) {\r
231                         int lev = levelPrev;\r
232                         if ((levelCurrent > levelPrev) && (visibleChars > 0))\r
233                                 lev |= SC_FOLDLEVELHEADERFLAG;\r
234                         if (lev != styler.LevelAt(lineCurrent)) {\r
235                                 styler.SetLevel(lineCurrent, lev);\r
236                         }\r
237                         lineCurrent++;\r
238                         levelPrev = levelCurrent;\r
239                         visibleChars = 0;\r
240                 }\r
241 \r
242                 if (!isspacechar(ch))\r
243                         visibleChars++;\r
244         }\r
245 \r
246         int flagsNext = styler.LevelAt(lineCurrent) & ~SC_FOLDLEVELNUMBERMASK;\r
247         styler.SetLevel(lineCurrent, levelPrev | flagsNext);\r
248 }\r
249 \r
250 static const char * const GAPWordListDesc[] = {\r
251         "Keywords 1",\r
252         "Keywords 2",\r
253         "Keywords 3 (unused)",\r
254         "Keywords 4 (unused)",\r
255         0\r
256 };\r
257 \r
258 LexerModule lmGAP(\r
259    SCLEX_GAP,\r
260    ColouriseGAPDoc,\r
261    "gap",\r
262    FoldGAPDoc,\r
263    GAPWordListDesc);\r