1// Scintilla source code edit control
2/** @file LexSorcus.cxx
3** Lexer for SORCUS installation files
4** Written by Eugen Bitter and Christoph Baumann at SORCUS Computer, Heidelberg Germany
5** Based on the ASM Lexer by The Black Horus
6**/
7
8// The License.txt file describes the conditions under which this software may be distributed.
9
10#include <stdlib.h>
11#include <string.h>
12#include <stdio.h>
13#include <stdarg.h>
14#include <assert.h>
15#include <ctype.h>
16
17#include <string>
18#include <string_view>
19
20#include "ILexer.h"
21#include "Scintilla.h"
22#include "SciLexer.h"
23
24#include "WordList.h"
25#include "LexAccessor.h"
26#include "Accessor.h"
27#include "StyleContext.h"
28#include "CharacterSet.h"
29#include "LexerModule.h"
30
31using namespace Lexilla;
32
33
34//each character a..z and A..Z + '_' can be part of a keyword
35//additionally numbers that follow 'M' can be contained in a keyword
36static inline bool IsSWordStart(const int ch, const int prev_ch)
37{
38 if (isalpha(ch) || (ch == '_') || ((isdigit(ch)) && (prev_ch == 'M')))
39 return true;
40
41 return false;
42}
43
44
45//only digits that are not preceded by 'M' count as a number
46static inline bool IsSorcusNumber(const int ch, const int prev_ch)
47{
48 if ((isdigit(ch)) && (prev_ch != 'M'))
49 return true;
50
51 return false;
52}
53
54
55//only = is a valid operator
56static inline bool IsSorcusOperator(const int ch)
57{
58 if (ch == '=')
59 return true;
60
61 return false;
62}
63
64
65static void ColouriseSorcusDoc(Sci_PositionU startPos, Sci_Position length, int initStyle, WordList *keywordlists[],
66 Accessor &styler)
67{
68
69 WordList &Command = *keywordlists[0];
70 WordList &Parameter = *keywordlists[1];
71 WordList &Constant = *keywordlists[2];
72
73 // Do not leak onto next line
74 if (initStyle == SCE_SORCUS_STRINGEOL)
75 initStyle = SCE_SORCUS_DEFAULT;
76
77 StyleContext sc(startPos, length, initStyle, styler);
78
79 for (; sc.More(); sc.Forward())
80 {
81
82 // Prevent SCE_SORCUS_STRINGEOL from leaking back to previous line
83 if (sc.atLineStart && (sc.state == SCE_SORCUS_STRING))
84 {
85 sc.SetState(SCE_SORCUS_STRING);
86 }
87
88 // Determine if the current state should terminate.
89 if (sc.state == SCE_SORCUS_OPERATOR)
90 {
91 if (!IsSorcusOperator(sc.ch))
92 {
93 sc.SetState(SCE_SORCUS_DEFAULT);
94 }
95 }
96 else if(sc.state == SCE_SORCUS_NUMBER)
97 {
98 if(!IsSorcusNumber(sc.ch, sc.chPrev))
99 {
100 sc.SetState(SCE_SORCUS_DEFAULT);
101 }
102 }
103 else if (sc.state == SCE_SORCUS_IDENTIFIER)
104 {
105 if (!IsSWordStart(sc.ch, sc.chPrev))
106 {
107 char s[100];
108
109 sc.GetCurrent(s, sizeof(s));
110
111 if (Command.InList(s))
112 {
113 sc.ChangeState(SCE_SORCUS_COMMAND);
114 }
115 else if (Parameter.InList(s))
116 {
117 sc.ChangeState(SCE_SORCUS_PARAMETER);
118 }
119 else if (Constant.InList(s))
120 {
121 sc.ChangeState(SCE_SORCUS_CONSTANT);
122 }
123
124 sc.SetState(SCE_SORCUS_DEFAULT);
125 }
126 }
127 else if (sc.state == SCE_SORCUS_COMMENTLINE )
128 {
129 if (sc.atLineEnd)
130 {
131 sc.SetState(SCE_SORCUS_DEFAULT);
132 }
133 }
134 else if (sc.state == SCE_SORCUS_STRING)
135 {
136 if (sc.ch == '\"')
137 {
138 sc.ForwardSetState(SCE_SORCUS_DEFAULT);
139 }
140 else if (sc.atLineEnd)
141 {
142 sc.ChangeState(SCE_SORCUS_STRINGEOL);
143 sc.ForwardSetState(SCE_SORCUS_DEFAULT);
144 }
145 }
146
147 // Determine if a new state should be entered.
148 if (sc.state == SCE_SORCUS_DEFAULT)
149 {
150 if ((sc.ch == ';') || (sc.ch == '\''))
151 {
152 sc.SetState(SCE_SORCUS_COMMENTLINE);
153 }
154 else if (IsSWordStart(sc.ch, sc.chPrev))
155 {
156 sc.SetState(SCE_SORCUS_IDENTIFIER);
157 }
158 else if (sc.ch == '\"')
159 {
160 sc.SetState(SCE_SORCUS_STRING);
161 }
162 else if (IsSorcusOperator(sc.ch))
163 {
164 sc.SetState(SCE_SORCUS_OPERATOR);
165 }
166 else if (IsSorcusNumber(sc.ch, sc.chPrev))
167 {
168 sc.SetState(SCE_SORCUS_NUMBER);
169 }
170 }
171
172 }
173 sc.Complete();
174}
175
176
177static const char* const SorcusWordListDesc[] = {"Command","Parameter", "Constant", 0};
178
179LexerModule lmSorc(SCLEX_SORCUS, ColouriseSorcusDoc, "sorcins", 0, SorcusWordListDesc);
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210