[anjuta-extras] scintilla: Update to scintilla 3.3.4



commit 989364d1d4e2178be9e325b2f5f67eabfd508565
Author: Sébastien Granjoux <seb sfo free fr>
Date:   Sun Jul 21 11:49:28 2013 +0200

    scintilla: Update to scintilla 3.3.4

 plugins/scintilla/properties/styles.properties     |   33 +-
 plugins/scintilla/scintilla/Makefile.am            |    7 +
 plugins/scintilla/scintilla/gtk/PlatGTK.cxx        |  124 +-
 plugins/scintilla/scintilla/gtk/ScintillaGTK.cxx   |  382 +--
 plugins/scintilla/scintilla/include/ILexer.h       |    2 +
 plugins/scintilla/scintilla/include/Platform.h     |   34 +-
 plugins/scintilla/scintilla/include/SciLexer.h     |   31 +
 plugins/scintilla/scintilla/include/Scintilla.h    |   18 +
 .../scintilla/scintilla/include/Scintilla.iface    |   73 +
 plugins/scintilla/scintilla/lexers.make            |    2 +
 plugins/scintilla/scintilla/lexers/LexA68k.cxx     |  149 +-
 plugins/scintilla/scintilla/lexers/LexAda.cxx      |   15 -
 plugins/scintilla/scintilla/lexers/LexAsn1.cxx     |    2 +-
 plugins/scintilla/scintilla/lexers/LexCPP.cxx      |   22 +-
 .../scintilla/scintilla/lexers/LexCoffeeScript.cxx |   36 +-
 plugins/scintilla/scintilla/lexers/LexECL.cxx      |   17 +-
 plugins/scintilla/scintilla/lexers/LexHaskell.cxx  | 1205 ++++++--
 plugins/scintilla/scintilla/lexers/LexLaTeX.cxx    |    6 +-
 plugins/scintilla/scintilla/lexers/LexLua.cxx      |   35 +-
 plugins/scintilla/scintilla/lexers/LexMatlab.cxx   |   87 +-
 plugins/scintilla/scintilla/lexers/LexModula.cxx   |   12 +-
 plugins/scintilla/scintilla/lexers/LexOthers.cxx   |    9 +-
 plugins/scintilla/scintilla/lexers/LexPerl.cxx     |  118 +-
 .../scintilla/scintilla/lexers/LexPowerShell.cxx   |   51 +-
 plugins/scintilla/scintilla/lexers/LexRuby.cxx     |    4 +-
 plugins/scintilla/scintilla/lexers/LexSTTXT.cxx    |  401 +++
 plugins/scintilla/scintilla/lexlib/Accessor.cxx    |    2 +-
 plugins/scintilla/scintilla/lexlib/Accessor.h      |    2 +-
 .../scintilla/lexlib/CharacterCategory.cxx         | 3303 ++++++++++++++++++++
 .../scintilla/scintilla/lexlib/CharacterCategory.h |   31 +
 plugins/scintilla/scintilla/lexlib/LexAccessor.h   |   18 +-
 plugins/scintilla/scintilla/lexlib/LexerModule.cxx |    6 +-
 plugins/scintilla/scintilla/lexlib/OptionSet.h     |    6 +-
 .../scintilla/scintilla/lexlib/PropSetSimple.cxx   |   23 +-
 plugins/scintilla/scintilla/lexlib/PropSetSimple.h |    1 -
 plugins/scintilla/scintilla/lexlib/StyleContext.h  |  172 +-
 plugins/scintilla/scintilla/lexlib/WordList.cxx    |   51 +-
 plugins/scintilla/scintilla/lexlib/WordList.h      |   12 +-
 plugins/scintilla/scintilla/src/AutoComplete.cxx   |  119 +-
 plugins/scintilla/scintilla/src/AutoComplete.h     |    6 +
 plugins/scintilla/scintilla/src/CallTip.cxx        |   24 +-
 plugins/scintilla/scintilla/src/CallTip.h          |    4 +-
 plugins/scintilla/scintilla/src/CaseConvert.cxx    |  630 ++++
 plugins/scintilla/scintilla/src/CaseConvert.h      |   47 +
 plugins/scintilla/scintilla/src/CaseFolder.cxx     |   68 +
 plugins/scintilla/scintilla/src/CaseFolder.h       |   45 +
 plugins/scintilla/scintilla/src/Catalogue.cxx      |    4 +-
 plugins/scintilla/scintilla/src/CellBuffer.cxx     |   38 +-
 plugins/scintilla/scintilla/src/CellBuffer.h       |   10 +-
 .../scintilla/scintilla/src/ContractionState.cxx   |    2 +
 plugins/scintilla/scintilla/src/Decoration.cxx     |    6 +-
 plugins/scintilla/scintilla/src/Decoration.h       |    4 +-
 plugins/scintilla/scintilla/src/Document.cxx       |  373 +--
 plugins/scintilla/scintilla/src/Document.h         |  107 +-
 plugins/scintilla/scintilla/src/Editor.cxx         |  666 +++--
 plugins/scintilla/scintilla/src/Editor.h           |  146 +-
 plugins/scintilla/scintilla/src/Indicator.cxx      |    3 +
 plugins/scintilla/scintilla/src/KeyMap.cxx         |   36 +-
 plugins/scintilla/scintilla/src/KeyMap.h           |    6 +-
 plugins/scintilla/scintilla/src/PerLine.cxx        |   27 +-
 plugins/scintilla/scintilla/src/PerLine.h          |    8 +-
 plugins/scintilla/scintilla/src/PositionCache.cxx  |  115 +-
 plugins/scintilla/scintilla/src/PositionCache.h    |   15 +-
 plugins/scintilla/scintilla/src/RESearch.cxx       |   75 +-
 plugins/scintilla/scintilla/src/RESearch.h         |    7 +-
 plugins/scintilla/scintilla/src/RunStyles.cxx      |   42 +-
 plugins/scintilla/scintilla/src/RunStyles.h        |    8 +-
 plugins/scintilla/scintilla/src/ScintillaBase.cxx  |   52 +-
 plugins/scintilla/scintilla/src/ScintillaBase.h    |    5 +-
 plugins/scintilla/scintilla/src/Selection.cxx      |   13 +-
 plugins/scintilla/scintilla/src/SplitVector.h      |    3 +-
 plugins/scintilla/scintilla/src/Style.cxx          |   27 +-
 plugins/scintilla/scintilla/src/Style.h            |    5 +-
 plugins/scintilla/scintilla/src/UnicodeFromUTF8.h  |   19 +
 plugins/scintilla/scintilla/src/ViewStyle.cxx      |  205 +-
 plugins/scintilla/scintilla/src/ViewStyle.h        |   31 +-
 plugins/scintilla/scintilla/src/XPM.cxx            |  179 +-
 plugins/scintilla/scintilla/src/XPM.h              |   43 +-
 78 files changed, 7562 insertions(+), 2163 deletions(-)
---
diff --git a/plugins/scintilla/properties/styles.properties b/plugins/scintilla/properties/styles.properties
index 98b59dc..6d6e455 100644
--- a/plugins/scintilla/properties/styles.properties
+++ b/plugins/scintilla/properties/styles.properties
@@ -42,7 +42,7 @@ keywords=*amplitude *assembly \
 *shell *shell section *solid section *specific heat *sradiate *static *step \
 *surface \
 *temperature *time *type \
-*variable *viscosity 
+*variable *viscosity
 
 arguments=elset engineering inc input line material name nset pin tie type write generate field variable 
history \
 stefan boltzmann absolute zero zero frequency steady state new old set change number shift \
@@ -1484,7 +1484,7 @@ lexer.$(file.patterns.COBOL)=COBOL
 
 word.characters.$(file.patterns.cobol)=$(chars.alpha)$(chars.numeric)$(chars.accented)_-
 
-# These keywords are case insensitive 
+# These keywords are case insensitive
 keywords.$(file.patterns.COBOL)=configuration data declaratives division environment environment-division 
file file-control function i-o i-o-control identification input input-output linkage local-storage output 
procedure program program-id receive-control section special-names working-storage
 keywords2.$(file.patterns.COBOL)=accept add alter apply assign call chain close compute continue control 
convert copy count delete display divide draw drop eject else enable end-accept end-add end-call end-chain 
end-compute end-delete end-display end-divide end-evaluate end-if end-invoke end-multiply end-perform 
end-read end-receive end-return end-rewrite end-search end-start end-string end-subtract end-unstring 
end-write erase evaluate examine exec execute exit go goback generate if ignore initialize initiate insert 
inspect invoke leave merge move multiply open otherwise perform print read receive release reload replace 
report reread rerun reserve reset return rewind rewrite rollback run search seek select send set sort start 
stop store string subtract sum suppress terminate then transform unlock unstring update use wait when wrap 
write
 keywords3.$(file.patterns.COBOL)=access acquire actual address advancing after all allowing alphabet 
alphabetic alphabetic-lower alphabetic-upper alphanumeric alphanumeric-edited also alternate and any are area 
areas as ascending at attribute author auto auto-hyphen-skip auto-skip automatic autoterminate 
background-color background-colour backward basis beep before beginning bell binary blank blink blinking 
block bold bottom box boxed by c01 c02 c03 c04 c05 c06 c07 c08 c09 c10 c11 c12 cancel cbl cd centered cf ch 
chaining changed character characters chart class clock-units cobol code code-set col collating color colour 
column com-reg comma command-line commit commitment common communication comp comp-0 comp-1 comp-2 comp-3 
comp-4 comp-5 comp-6 comp-x compression computational computational-1 computational-2 computational-3 
computational-4 computational-5 computational-6 computational-x computational console contains content 
control-area controls conversion converting core-i
 ndex corr corresponding crt crt-under csp currency current-date cursor cycle cyl-index cyl-overflow date 
date-compiled date-written day day-of-week dbcs de debug debug-contents debug-item debug-line debug-name 
debug-sub-1 debug-sub-2 debug-sub-3 debugging decimal-point default delimited delimiter depending descending 
destination detail disable disk disp display-1 display-st down duplicates dynamic echo egcs egi emi 
empty-check encryption end end-of-page ending enter entry eol eop eos equal equals error escape esi every 
exceeds exception excess-3 exclusive exhibit extend extended-search external externally-described-key factory 
false fd fh--fcd fh--keydef file-id file-limit file-limits file-prefix filler final first fixed footing for 
foreground-color foreground-colour footing format from full giving global greater grid group heading high 
high-value high-values highlight id in index indexed indic indicate indicator indicators inheriting initial 
installation into invalid invoke
 d is japanese just justified kanji kept key keyboard label last leading left left-justify leftline length 
length-check less limit limits lin linage linage-counter line line-counter lines lock lock-holding locking 
low low-value low-values lower lowlight manual mass-update master-index memory message method mode modified 
modules more-labels multiple name named national national-edited native nchar negative next no no-echo 
nominal not note nstd-reels null nulls number numeric numeric-edited numeric-fill o-fill object 
object-computer object-storage occurs of off omitted on oostackptr optional or order organization other 
others overflow overline packed-decimal padding page page-counter packed-decimal paragraph password pf ph pic 
picture plus pointer pop-up pos position positioning positive previous print-control print-switch printer 
printer-1 printing prior private procedure-pointer procedures proceed process processing prompt protected 
public purge queue quote quotes random rang
 e rd readers ready record record-overflow recording records redefines reel reference references relative 
remainder remarks removal renames reorg-criteria repeated replacing reporting reports required resident 
return-code returning reverse reverse-video reversed rf rh right right-justify rolling rounded s01 s02 s03 
s04 s05 same screen scroll sd secure security segment segment-limit selective self selfclass sentence 
separate sequence sequential service setshadow shift-in shift-out sign size skip1 skip2 skip3 sort-control 
sort-core-size sort-file-size sort-merge sort-message sort-mode-size sort-option sort-return source 
source-computer space spaces space-fill spaces standard standard-1 standard-2 starting status sub-queue-1 
sub-queue-2 sub-queue-3 subfile super symbolic sync synchronized sysin sysipt syslst sysout syspch syspunch 
system-info tab tallying tape terminal terminal-info test text than through thru time time-of-day time-out 
timeout times title to top totaled totaling
  trace track-area track-limit tracks trailing trailing-sign transaction true type typedef underline 
underlined unequal unit until up updaters upon upper upsi-0 upsi-1 upsi-2 upsi-3 upsi-4 upsi-5 upsi-6 upsi-7 
usage user using value values variable varying when-compiled window with words write-only write-verify 
writerszero zero zero-fill zeros zeroes
@@ -2155,7 +2155,7 @@ comment.block.csound=;
 ###############################################################################
 # From css.properties
 # Define SciTE settings for CSS files
-# Jakub Vr�na - jakub vrana cz
+# Jakub Vrána - jakub vrana cz
 # Updated Andy Holder - Jan 2011
 
 filter.css=CSS (css)|*.css|
@@ -3524,7 +3524,7 @@ keywords2.$(file.patterns.mako)=$(keywordclass.javascript)
 keywords3.$(file.patterns.mako)=$(keywordclass.vb)
 # Python keywords are possible inside embedded Python
 keywords4.$(file.patterns.mako)=$(keywordclass.python) include namespace inherit \
-call doc text page endclass endexcept endfinally endfor endif endtry endwhile
+call doc text page endclass endexcept endfinally endfor endif endtry endwhile block
 # PHP keywords are possible inside embedded PHP
 keywords5.$(file.patterns.mako)=$(keywordclass.php)
 # SGML / DTD keywords
@@ -4442,11 +4442,10 @@ keywords2.$(file.patterns.metafun)=$(keywordclass.metafun.all)
 
 ##  Metapost fold points
 ## keywords4  = fold beginning; keywords5 = fold ending.
-keywords4.$(file.patterns.metapost)=beginfig for verbatimtex def begingroup
-if btex forsuffixes \
- vardef primarydef
-keywords5.$(file.patterns.metapost)=etex fi endfig endgroup end endfor endif
-enddef
+keywords4.$(file.patterns.metapost)=beginfig for verbatimtex def begingroup \
+    if btex forsuffixes vardef primarydef
+keywords5.$(file.patterns.metapost)=etex fi endfig endgroup end endfor endif \
+    enddef
 
 import metafun-scite.properties
 
@@ -6082,7 +6081,7 @@ keywords3.$(file.patterns.rebol)=action! any-block! any-function! any-string! an
  port! refinement! routine! series! set-path! set-word! string! struct! symbol! tag! \
  time! tuple! unset! url! word!
 
-word.chars.rebol=$(chars.alpha)$(chars.numeric)?!.�+-*&|=_~
+word.chars.rebol=$(chars.alpha)$(chars.numeric)?!.\92+-*&|=_~
 word.characters.$(file.patterns.rebol)=$(word.chars.rebol)
 
 comment.block.rebol=;
@@ -8233,6 +8232,8 @@ keywords.$(file.patterns.yaml)=true false yes no
        style.cpp.22=$(style.anjuta.string)
 # Preprocessor stream comment
        style.cpp.23=$(style.anjuta.preprocessor)
+# Preprocessor stream doc comment
+       style.cpp.24=$(style.anjuta.preprocessor)
 # White space
        style.cpp.64=$(style.anjuta.whitespace)
 # Comment: /* */.
@@ -8279,6 +8280,8 @@ keywords.$(file.patterns.yaml)=true false yes no
        style.cpp.86=$(style.anjuta.string)
 # Preprocessor stream comment
        style.cpp.87=$(style.anjuta.preprocessor)
+# Preprocessor stream doc comment
+       style.cpp.88=$(style.anjuta.preprocessor)
 
 
 
@@ -8919,6 +8922,16 @@ keywords.$(file.patterns.yaml)=true false yes no
        style.haskell.13=$(style.anjuta.comment)
 # block comment
        style.haskell.14=$(style.anjuta.comment)
+# block comment 2
+       style.haskell.15=$(style.anjuta.comment)
+# block comment 3
+       style.haskell.16=$(style.anjuta.comment)
+# pragma
+       style.haskell.17=$(style.anjuta.preprocessor)
+# preprocessor
+       style.haskell.18=$(style.anjuta.preprocessor)
+# End of line where string is not closed
+       style.haskell.19=$(style.anjuta.error)
 
 
 
diff --git a/plugins/scintilla/scintilla/Makefile.am b/plugins/scintilla/scintilla/Makefile.am
index 74eb600..6011653 100644
--- a/plugins/scintilla/scintilla/Makefile.am
+++ b/plugins/scintilla/scintilla/Makefile.am
@@ -22,6 +22,11 @@ libanjuta_scintilla_la_SOURCES =\
        src/AutoComplete.h \
        src/CallTip.cxx \
        src/CallTip.h \
+       src/CaseConvert.cxx \
+       src/CaseConvert.h \
+       src/CaseFolder.cxx \
+       src/CaseFolder.h \
+       src/UnicodeFromUTF8.h \
        src/Catalogue.cxx \
        src/Catalogue.h \
        src/CellBuffer.cxx \
@@ -71,6 +76,8 @@ libanjuta_scintilla_la_SOURCES =\
        lexlib/Accessor.h \
        lexlib/CharacterSet.cxx \
        lexlib/CharacterSet.h \
+       lexlib/CharacterCategory.cxx \
+       lexlib/CharacterCategory.h \
        lexlib/LexAccessor.h \
        lexlib/LexerBase.cxx \
        lexlib/LexerBase.h \
diff --git a/plugins/scintilla/scintilla/gtk/PlatGTK.cxx b/plugins/scintilla/scintilla/gtk/PlatGTK.cxx
index c228047..a6ae84e 100644
--- a/plugins/scintilla/scintilla/gtk/PlatGTK.cxx
+++ b/plugins/scintilla/scintilla/gtk/PlatGTK.cxx
@@ -9,6 +9,7 @@
 #include <stddef.h>
 #include <math.h>
 
+#include <string>
 #include <vector>
 #include <map>
 
@@ -184,7 +185,7 @@ public:
                        width[i] = 0;
                }
        }
-       XYPOSITION CharWidth(unsigned char ch, encodingType et_) {
+       XYPOSITION CharWidth(unsigned char ch, encodingType et_) const {
                XYPOSITION w = 0;
                FontMutexLock();
                if ((ch <= 127) && (et == et_)) {
@@ -259,6 +260,7 @@ class FontCached : Font {
 public:
        static FontID FindOrCreate(const FontParameters &fp);
        static void ReleaseId(FontID fid_);
+       static void ReleaseAll();
 };
 
 FontCached *FontCached::first = 0;
@@ -299,11 +301,9 @@ FontID FontCached::FindOrCreate(const FontParameters &fp) {
        }
        if (ret == 0) {
                FontCached *fc = new FontCached(fp);
-               if (fc) {
-                       fc->next = first;
-                       first = fc;
-                       ret = fc->fid;
-               }
+               fc->next = first;
+               first = fc;
+               ret = fc->fid;
        }
        FontMutexUnlock();
        return ret;
@@ -328,6 +328,12 @@ void FontCached::ReleaseId(FontID fid_) {
        FontMutexUnlock();
 }
 
+void FontCached::ReleaseAll() {
+       while (first) {
+               ReleaseId(first->GetID());
+       }
+}
+
 FontID FontCached::CreateNewFont(const FontParameters &fp) {
        PangoFontDescription *pfd = pango_font_description_new();
        if (pfd) {
@@ -831,8 +837,8 @@ void SurfaceImpl::Copy(PRectangle rc, Point from, Surface &surfaceSource) {
        }
 }
 
-char *UTF8FromLatin1(const char *s, int &len) {
-       char *utfForm = new char[len*2+1];
+std::string UTF8FromLatin1(const char *s, int len) {
+       std::string utfForm(len*2 + 1, '\0');
        size_t lenU = 0;
        for (int i=0;i<len;i++) {
                unsigned int uch = static_cast<unsigned char>(s[i]);
@@ -843,27 +849,26 @@ char *UTF8FromLatin1(const char *s, int &len) {
                        utfForm[lenU++] = static_cast<char>(0x80 | (uch & 0x3f));
                }
        }
-       utfForm[lenU] = '\0';
-       len = lenU;
+       utfForm.resize(lenU);
        return utfForm;
 }
 
-static char *UTF8FromIconv(const Converter &conv, const char *s, int &len) {
+static std::string UTF8FromIconv(const Converter &conv, const char *s, int len) {
        if (conv) {
-               char *utfForm = new char[len*3+1];
+               std::string utfForm(len*3+1, '\0');
                char *pin = const_cast<char *>(s);
                size_t inLeft = len;
-               char *pout = utfForm;
+               char *putf = &utfForm[0];
+               char *pout = putf;
                size_t outLeft = len*3+1;
                size_t conversions = conv.Convert(&pin, &inLeft, &pout, &outLeft);
                if (conversions != ((size_t)(-1))) {
                        *pout = '\0';
-                       len = pout - utfForm;
+                       utfForm.resize(pout - putf);
                        return utfForm;
                }
-               delete []utfForm;
        }
-       return 0;
+       return std::string();
 }
 
 // Work out how many bytes are in a character by trying to convert using iconv,
@@ -901,18 +906,16 @@ void SurfaceImpl::DrawTextBase(PRectangle rc, Font &font_, XYPOSITION ybase, con
        if (context) {
                XYPOSITION xText = rc.left;
                if (PFont(font_)->pfd) {
-                       char *utfForm = 0;
+                       std::string utfForm;
                        if (et == UTF8) {
                                pango_layout_set_text(layout, s, len);
                        } else {
-                               if (!utfForm) {
-                                       SetConverter(PFont(font_)->characterSet);
-                                       utfForm = UTF8FromIconv(conv, s, len);
-                               }
-                               if (!utfForm) { // iconv failed so treat as Latin1
+                               SetConverter(PFont(font_)->characterSet);
+                               utfForm = UTF8FromIconv(conv, s, len);
+                               if (utfForm.empty()) {  // iconv failed so treat as Latin1
                                        utfForm = UTF8FromLatin1(s, len);
                                }
-                               pango_layout_set_text(layout, utfForm, len);
+                               pango_layout_set_text(layout, utfForm.c_str(), utfForm.length());
                        }
                        pango_layout_set_font_description(layout, PFont(font_)->pfd);
                        pango_cairo_update_layout(context, layout);
@@ -923,7 +926,6 @@ void SurfaceImpl::DrawTextBase(PRectangle rc, Font &font_, XYPOSITION ybase, con
 #endif
                        cairo_move_to(context, xText, ybase);
                        pango_cairo_show_layout_line(context, pll);
-                       delete []utfForm;
                }
        }
 }
@@ -1020,20 +1022,20 @@ void SurfaceImpl::MeasureWidths(Font &font_, const char *s, int len, XYPOSITION
                                int positionsCalculated = 0;
                                if (et == dbcs) {
                                        SetConverter(PFont(font_)->characterSet);
-                                       char *utfForm = UTF8FromIconv(conv, s, len);
-                                       if (utfForm) {
+                                       std::string utfForm = UTF8FromIconv(conv, s, len);
+                                       if (!utfForm.empty()) {
                                                // Convert to UTF-8 so can ask Pango for widths, then
                                                // Loop through UTF-8 and DBCS forms, taking account of 
different
                                                // character byte lengths.
                                                Converter convMeasure("UCS-2", CharacterSetID(characterSet), 
false);
-                                               pango_layout_set_text(layout, utfForm, strlen(utfForm));
+                                               pango_layout_set_text(layout, utfForm.c_str(), 
strlen(utfForm.c_str()));
                                                int i = 0;
                                                int clusterStart = 0;
-                                               ClusterIterator iti(layout, strlen(utfForm));
+                                               ClusterIterator iti(layout, strlen(utfForm.c_str()));
                                                while (!iti.finished) {
                                                        iti.Next();
                                                        int clusterEnd = iti.curIndex;
-                                                       int places = g_utf8_strlen(utfForm + clusterStart, 
clusterEnd - clusterStart);
+                                                       int places = g_utf8_strlen(utfForm.c_str() + 
clusterStart, clusterEnd - clusterStart);
                                                        int place = 1;
                                                        while (clusterStart < clusterEnd) {
                                                                size_t lenChar = 
MultiByteLenFromIconv(convMeasure, s+i, len-i);
@@ -1041,38 +1043,36 @@ void SurfaceImpl::MeasureWidths(Font &font_, const char *s, int len, XYPOSITION
                                                                        positions[i++] = iti.position - 
(places - place) * iti.distance / places;
                                                                        positionsCalculated++;
                                                                }
-                                                               clusterStart += 
UTF8CharLength(utfForm+clusterStart);
+                                                               clusterStart += 
UTF8CharLength(utfForm.c_str()+clusterStart);
                                                                place++;
                                                        }
                                                }
-                                               delete []utfForm;
                                                PLATFORM_ASSERT(i == lenPositions);
                                        }
                                }
                                if (positionsCalculated < 1 ) {
                                        // Either Latin1 or DBCS conversion failed so treat as Latin1.
                                        SetConverter(PFont(font_)->characterSet);
-                                       char *utfForm = UTF8FromIconv(conv, s, len);
-                                       if (!utfForm) {
+                                       std::string utfForm = UTF8FromIconv(conv, s, len);
+                                       if (utfForm.empty()) {
                                                utfForm = UTF8FromLatin1(s, len);
                                        }
-                                       pango_layout_set_text(layout, utfForm, len);
+                                       pango_layout_set_text(layout, utfForm.c_str(), utfForm.length());
                                        int i = 0;
                                        int clusterStart = 0;
                                        // Each Latin1 input character may take 1 or 2 bytes in UTF-8
                                        // and groups of up to 3 may be represented as ligatures.
-                                       ClusterIterator iti(layout, strlen(utfForm));
+                                       ClusterIterator iti(layout, utfForm.length());
                                        while (!iti.finished) {
                                                iti.Next();
                                                int clusterEnd = iti.curIndex;
-                                               int ligatureLength = g_utf8_strlen(utfForm + clusterStart, 
clusterEnd - clusterStart);
+                                               int ligatureLength = g_utf8_strlen(utfForm.c_str() + 
clusterStart, clusterEnd - clusterStart);
                                                PLATFORM_ASSERT(ligatureLength > 0 && ligatureLength <= 3);
                                                for (int charInLig=0; charInLig<ligatureLength; charInLig++) {
                                                        positions[i++] = iti.position - (ligatureLength - 1 - 
charInLig) * iti.distance / ligatureLength;
                                                }
                                                clusterStart = clusterEnd;
                                        }
-                                       delete []utfForm;
                                        PLATFORM_ASSERT(i == lenPositions);
                                }
                        }
@@ -1092,20 +1092,18 @@ void SurfaceImpl::MeasureWidths(Font &font_, const char *s, int len, XYPOSITION
 XYPOSITION SurfaceImpl::WidthText(Font &font_, const char *s, int len) {
        if (font_.GetID()) {
                if (PFont(font_)->pfd) {
-                       char *utfForm = 0;
+                       std::string utfForm;
                        pango_layout_set_font_description(layout, PFont(font_)->pfd);
                        PangoRectangle pos;
                        if (et == UTF8) {
                                pango_layout_set_text(layout, s, len);
                        } else {
-                               if (!utfForm) { // use iconv
-                                       SetConverter(PFont(font_)->characterSet);
-                                       utfForm = UTF8FromIconv(conv, s, len);
-                               }
-                               if (!utfForm) { // iconv failed so treat as Latin1
+                               SetConverter(PFont(font_)->characterSet);
+                               utfForm = UTF8FromIconv(conv, s, len);
+                               if (utfForm.empty()) {  // iconv failed so treat as Latin1
                                        utfForm = UTF8FromLatin1(s, len);
                                }
-                               pango_layout_set_text(layout, utfForm, len);
+                               pango_layout_set_text(layout, utfForm.c_str(), utfForm.length());
                        }
 #ifdef PANGO_VERSION
                        PangoLayoutLine *pangoLine = pango_layout_get_line_readonly(layout,0);
@@ -1113,7 +1111,6 @@ XYPOSITION SurfaceImpl::WidthText(Font &font_, const char *s, int len) {
                        PangoLayoutLine *pangoLine = pango_layout_get_line(layout,0);
 #endif
                        pango_layout_line_get_extents(pangoLine, NULL, &pos);
-                       delete []utfForm;
                        return doubleFromPangoUnits(pos.width);
                }
                return 1;
@@ -1883,30 +1880,26 @@ void ListBoxX::ClearRegisteredImages() {
 void ListBoxX::SetList(const char *listText, char separator, char typesep) {
        Clear();
        int count = strlen(listText) + 1;
-       char *words = new char[count];
-       if (words) {
-               memcpy(words, listText, count);
-               char *startword = words;
-               char *numword = NULL;
-               int i = 0;
-               for (; words[i]; i++) {
-                       if (words[i] == separator) {
-                               words[i] = '\0';
-                               if (numword)
-                                       *numword = '\0';
-                               Append(startword, numword?atoi(numword + 1):-1);
-                               startword = words + i + 1;
-                               numword = NULL;
-                       } else if (words[i] == typesep) {
-                               numword = words + i;
-                       }
-               }
-               if (startword) {
+       std::vector<char> words(listText, listText+count);
+       char *startword = &words[0];
+       char *numword = NULL;
+       int i = 0;
+       for (; words[i]; i++) {
+               if (words[i] == separator) {
+                       words[i] = '\0';
                        if (numword)
                                *numword = '\0';
                        Append(startword, numword?atoi(numword + 1):-1);
+                       startword = &words[0] + i + 1;
+                       numword = NULL;
+               } else if (words[i] == typesep) {
+                       numword = &words[0] + i;
                }
-               delete []words;
+       }
+       if (startword) {
+               if (numword)
+                       *numword = '\0';
+               Append(startword, numword?atoi(numword + 1):-1);
        }
 }
 
@@ -2165,5 +2158,6 @@ void Platform_Initialise() {
 }
 
 void Platform_Finalise() {
+       FontCached::ReleaseAll();
        FontMutexFree();
 }
diff --git a/plugins/scintilla/scintilla/gtk/ScintillaGTK.cxx 
b/plugins/scintilla/scintilla/gtk/ScintillaGTK.cxx
index 20c398b..82ca0b3 100644
--- a/plugins/scintilla/scintilla/gtk/ScintillaGTK.cxx
+++ b/plugins/scintilla/scintilla/gtk/ScintillaGTK.cxx
@@ -14,6 +14,7 @@
 #include <string>
 #include <vector>
 #include <map>
+#include <algorithm>
 
 #include <gtk/gtk.h>
 #include <gdk/gdkkeysyms.h>
@@ -30,7 +31,6 @@
 #ifdef SCI_LEXER
 #include "SciLexer.h"
 #endif
-#include "SVector.h"
 #include "SplitVector.h"
 #include "Partitioning.h"
 #include "RunStyles.h"
@@ -46,12 +46,14 @@
 #include "ViewStyle.h"
 #include "Decoration.h"
 #include "CharClassify.h"
+#include "CaseFolder.h"
 #include "Document.h"
 #include "Selection.h"
 #include "PositionCache.h"
 #include "Editor.h"
 #include "ScintillaBase.h"
 #include "UniConversion.h"
+#include "CaseConvert.h"
 
 #include "scintilla-marshal.h"
 
@@ -109,7 +111,7 @@ static GdkWindow *PWindow(const Window &w) {
 using namespace Scintilla;
 #endif
 
-extern char *UTF8FromLatin1(const char *s, int &len);
+extern std::string UTF8FromLatin1(const char *s, int len);
 
 class ScintillaGTK : public ScintillaBase {
        _ScintillaObject *sci;
@@ -118,12 +120,12 @@ class ScintillaGTK : public ScintillaBase {
        Window scrollbarh;
        GtkAdjustment *adjustmentv;
        GtkAdjustment *adjustmenth;
-       int scrollBarWidth;
-       int scrollBarHeight;
+       int verticalScrollBarWidth;
+       int horizontalScrollBarHeight;
 
        SelectionText primary;
 
-       GdkEventButton evbtn;
+       GdkEventButton *evbtn;
        bool capturedMouse;
        bool dragWasDropped;
        int lastKey;
@@ -173,7 +175,7 @@ private:
        virtual bool DragThreshold(Point ptStart, Point ptNow);
        virtual void StartDrag();
        int TargetAsUTF8(char *text);
-       int EncodedFromUTF8(char *utf8, char *encoded);
+       int EncodedFromUTF8(char *utf8, char *encoded) const;
        virtual bool ValidCodePage(int codePage) const;
 public:        // Public for scintilla_send_message
        virtual sptr_t WndProc(unsigned int iMessage, uptr_t wParam, sptr_t lParam);
@@ -186,7 +188,6 @@ private:
        virtual bool PaintContains(PRectangle rc);
        void FullPaint();
        virtual PRectangle GetClientRectangle();
-       void SyncPaint(PRectangle rc);
        virtual void ScrollText(int linesToMove);
        virtual void SetVerticalScrollPos();
        virtual void SetHorizontalScrollPos();
@@ -233,8 +234,10 @@ private:
        gint FocusOutThis(GtkWidget *widget);
        static gint FocusOut(GtkWidget *widget, GdkEventFocus *event);
        static void SizeRequest(GtkWidget *widget, GtkRequisition *requisition);
+#if GTK_CHECK_VERSION(3,0,0)
        static void GetPreferredWidth(GtkWidget *widget, gint *minimalWidth, gint *naturalWidth);
        static void GetPreferredHeight(GtkWidget *widget, gint *minimalHeight, gint *naturalHeight);
+#endif
        static void SizeAllocate(GtkWidget *widget, GtkAllocation *allocation);
 #if GTK_CHECK_VERSION(3,0,0)
        gboolean DrawTextThis(cairo_t *cr);
@@ -280,7 +283,6 @@ private:
        static void SelectionGet(GtkWidget *widget, GtkSelectionData *selection_data,
                                 guint info, guint time);
        static gint SelectionClear(GtkWidget *widget, GdkEventSelection *selection_event);
-       static void DragBegin(GtkWidget *widget, GdkDragContext *context);
        gboolean DragMotionThis(GdkDragContext *context, gint x, gint y, guint dragtime);
        static gboolean DragMotion(GtkWidget *widget, GdkDragContext *context,
                                   gint x, gint y, guint dragtime);
@@ -356,8 +358,8 @@ static ScintillaGTK *ScintillaFromWidget(GtkWidget *widget) {
 
 ScintillaGTK::ScintillaGTK(_ScintillaObject *sci_) :
                adjustmentv(0), adjustmenth(0),
-               scrollBarWidth(30), scrollBarHeight(30),
-               capturedMouse(false), dragWasDropped(false),
+               verticalScrollBarWidth(30), horizontalScrollBarHeight(30),
+               evbtn(0), capturedMouse(false), dragWasDropped(false),
                lastKey(0), rectangularSelectionModifier(SCMOD_CTRL), parentClass(0),
                im_context(NULL),
                lastWheelMouseDirection(0),
@@ -373,12 +375,12 @@ ScintillaGTK::ScintillaGTK(_ScintillaObject *sci_) :
 #endif
 
 #if PLAT_GTK_WIN32
-       // There does not seem to be a real standard for indicating that the clipboard
+       // There does not seem to be a real standard for indicating that the clipboard
        // contains a rectangular selection, so copy Developer Studio.
        cfColumnSelect = static_cast<CLIPFORMAT>(
                ::RegisterClipboardFormat("MSDEVColumnSelect"));
 
-       // Get intellimouse parameters when running on win32; otherwise use
+       // Get intellimouse parameters when running on win32; otherwise use
        // reasonable default
 #ifndef SPI_GETWHEELSCROLLLINES
 #define SPI_GETWHEELSCROLLLINES   104
@@ -395,6 +397,10 @@ ScintillaGTK::ScintillaGTK(_ScintillaObject *sci_) :
 
 ScintillaGTK::~ScintillaGTK() {
        g_idle_remove_by_data(this);
+       if (evbtn) {
+               gdk_event_free(reinterpret_cast<GdkEvent *>(evbtn));
+               evbtn = 0;
+       }
 }
 
 static void UnRefCursor(GdkCursor *cursor) {
@@ -676,6 +682,8 @@ void ScintillaGTK::SizeRequest(GtkWidget *widget, GtkRequisition *requisition) {
 #endif
 }
 
+#if GTK_CHECK_VERSION(3,0,0)
+
 void ScintillaGTK::GetPreferredWidth(GtkWidget *widget, gint *minimalWidth, gint *naturalWidth) {
        GtkRequisition requisition;
        SizeRequest(widget, &requisition);
@@ -688,6 +696,8 @@ void ScintillaGTK::GetPreferredHeight(GtkWidget *widget, gint *minimalHeight, gi
        *minimalHeight = *naturalHeight = requisition.height;
 }
 
+#endif
+
 void ScintillaGTK::SizeAllocate(GtkWidget *widget, GtkAllocation *allocation) {
        ScintillaGTK *sciThis = ScintillaFromWidget(widget);
        try {
@@ -827,47 +837,46 @@ bool ScintillaGTK::DragThreshold(Point ptStart, Point ptNow) {
 }
 
 void ScintillaGTK::StartDrag() {
+       PLATFORM_ASSERT(evbtn != 0);
        dragWasDropped = false;
        inDragDrop = ddDragging;
        GtkTargetList *tl = gtk_target_list_new(clipboardCopyTargets, nClipboardCopyTargets);
        gtk_drag_begin(GTK_WIDGET(PWidget(wMain)),
                       tl,
                       static_cast<GdkDragAction>(GDK_ACTION_COPY | GDK_ACTION_MOVE),
-                      evbtn.button,
-                      reinterpret_cast<GdkEvent *>(&evbtn));
+                      evbtn->button,
+                      reinterpret_cast<GdkEvent *>(evbtn));
 }
 
-static char *ConvertText(int *lenResult, char *s, size_t len, const char *charSetDest,
+static std::string ConvertText(const char *s, size_t len, const char *charSetDest,
        const char *charSetSource, bool transliterations, bool silent=false) {
        // s is not const because of different versions of iconv disagreeing about const
-       *lenResult = 0;
-       char *destForm = 0;
+       std::string destForm;
        Converter conv(charSetDest, charSetSource, transliterations);
        if (conv) {
-               destForm = new char[len*3+1];
-               char *pin = s;
-               size_t inLeft = len;
-               char *pout = destForm;
                size_t outLeft = len*3+1;
+               destForm = std::string(outLeft, '\0');
+               // g_iconv does not actually write to its input argument so safe to cast away const
+               char *pin = const_cast<char *>(s);
+               size_t inLeft = len;
+               char *putf = &destForm[0];
+               char *pout = putf;
                size_t conversions = conv.Convert(&pin, &inLeft, &pout, &outLeft);
                if (conversions == ((size_t)(-1))) {
-                       if (!silent)
-                               fprintf(stderr, "iconv %s->%s failed for %s\n",
-                                       charSetSource, charSetDest, static_cast<char *>(s));
-                       delete []destForm;
-                       destForm = 0;
+                       if (!silent) {
+                               if (len == 1)
+                                       fprintf(stderr, "iconv %s->%s failed for %0x '%s'\n",
+                                               charSetSource, charSetDest, (unsigned char)(*s), s);
+                               else
+                                       fprintf(stderr, "iconv %s->%s failed for %s\n",
+                                               charSetSource, charSetDest, s);
+                       }
+                       destForm = std::string();
                } else {
-//fprintf(stderr, "iconv OK %s %d\n", destForm, pout - destForm);
-                       *pout = '\0';
-                       *lenResult = pout - destForm;
+                       destForm.resize(pout - putf);
                }
        } else {
-fprintf(stderr, "Can not iconv %s %s\n", charSetDest, charSetSource);
-       }
-       if (!destForm) {
-               destForm = new char[1];
-               destForm[0] = '\0';
-               *lenResult = 0;
+               fprintf(stderr, "Can not iconv %s %s\n", charSetDest, charSetSource);
        }
        return destForm;
 }
@@ -884,32 +893,24 @@ int ScintillaGTK::TargetAsUTF8(char *text) {
                // Need to convert
                const char *charSetBuffer = CharacterSetID();
                if (*charSetBuffer) {
-//~ fprintf(stderr, "AsUTF8 %s %d  %0d-%0d\n", charSetBuffer, targetLength, targetStart, targetEnd);
-                       char *s = new char[targetLength];
-                       if (s) {
-                               pdoc->GetCharRange(s, targetStart, targetLength);
-//~ fprintf(stderr, "    \"%s\"\n", s);
-                               if (text) {
-                                       char *tmputf = ConvertText(&targetLength, s, targetLength, "UTF-8", 
charSetBuffer, false);
-                                       memcpy(text, tmputf, targetLength);
-                                       delete []tmputf;
-//~ fprintf(stderr, "    \"%s\"\n", text);
-                               }
-                               delete []s;
+                       std::string s = RangeText(targetStart, targetEnd);
+                       std::string tmputf = ConvertText(&s[0], targetLength, "UTF-8", charSetBuffer, false);
+                       if (text) {
+                               memcpy(text, tmputf.c_str(), tmputf.length());
                        }
+                       return tmputf.length();
                } else {
                        if (text) {
                                pdoc->GetCharRange(text, targetStart, targetLength);
                        }
                }
        }
-//~ fprintf(stderr, "Length = %d bytes\n", targetLength);
        return targetLength;
 }
 
 // Translates a nul terminated UTF8 string into the document encoding.
 // Return the length of the result in bytes.
-int ScintillaGTK::EncodedFromUTF8(char *utf8, char *encoded) {
+int ScintillaGTK::EncodedFromUTF8(char *utf8, char *encoded) const {
        int inputLength = (lengthForEncode >= 0) ? lengthForEncode : strlen(utf8);
        if (IsUnicodeMode()) {
                if (encoded) {
@@ -920,15 +921,11 @@ int ScintillaGTK::EncodedFromUTF8(char *utf8, char *encoded) {
                // Need to convert
                const char *charSetBuffer = CharacterSetID();
                if (*charSetBuffer) {
-                       int outLength = 0;
-                       char *tmpEncoded = ConvertText(&outLength, utf8, inputLength, charSetBuffer, "UTF-8", 
true);
-                       if (tmpEncoded) {
-                               if (encoded) {
-                                       memcpy(encoded, tmpEncoded, outLength);
-                               }
-                               delete []tmpEncoded;
+                       std::string tmpEncoded = ConvertText(utf8, inputLength, charSetBuffer, "UTF-8", true);
+                       if (encoded) {
+                               memcpy(encoded, tmpEncoded.c_str(), tmpEncoded.length());
                        }
-                       return outLength;
+                       return tmpEncoded.length();
                } else {
                        if (encoded) {
                                memcpy(encoded, utf8, inputLength);
@@ -966,7 +963,7 @@ sptr_t ScintillaGTK::WndProc(unsigned int iMessage, uptr_t wParam, sptr_t lParam
 
 #ifdef SCI_LEXER
                case SCI_LOADLEXERLIBRARY:
-                        LexerManager::GetInstance()->Load(reinterpret_cast<const char*>(lParam));
+                       LexerManager::GetInstance()->Load(reinterpret_cast<const char*>(lParam));
                        break;
 #endif
                case SCI_TARGETASUTF8:
@@ -1098,9 +1095,9 @@ void ScintillaGTK::FullPaint() {
 PRectangle ScintillaGTK::GetClientRectangle() {
        PRectangle rc = wMain.GetClientPosition();
        if (verticalScrollBarVisible)
-               rc.right -= scrollBarWidth;
+               rc.right -= verticalScrollBarWidth;
        if (horizontalScrollBarVisible && (wrapState == eWrapNone))
-               rc.bottom -= scrollBarHeight;
+               rc.bottom -= horizontalScrollBarHeight;
        // Move to origin
        rc.right -= rc.left;
        rc.bottom -= rc.top;
@@ -1109,30 +1106,6 @@ PRectangle ScintillaGTK::GetClientRectangle() {
        return rc;
 }
 
-// Synchronously paint a rectangle of the window.
-void ScintillaGTK::SyncPaint(PRectangle rc) {
-       paintState = painting;
-       rcPaint = rc;
-       PRectangle rcClient = GetClientRectangle();
-       paintingAllText = rcPaint.Contains(rcClient);
-       if (PWindow(wText)) {
-               Surface *sw = Surface::Allocate(SC_TECHNOLOGY_DEFAULT);
-               if (sw) {
-                       cairo_t *cr = gdk_cairo_create(PWindow(wText));
-                       sw->Init(cr, PWidget(wText));
-                       Paint(sw, rc);
-                       sw->Release();
-                       delete sw;
-                       cairo_destroy(cr);
-               }
-       }
-       if (paintState == paintAbandoned) {
-               // Painting area was insufficient to cover new styling or brace highlight positions
-               FullPaint();
-       }
-       paintState = notPainting;
-}
-
 void ScintillaGTK::ScrollText(int linesToMove) {
        int diff = vs.lineHeight * -linesToMove;
        //Platform::DebugPrintf("ScintillaGTK::ScrollText %d %d %0d,%0d %0d,%0d\n", linesToMove, diff,
@@ -1267,29 +1240,6 @@ const char *ScintillaGTK::CharacterSetID() const {
        return ::CharacterSetID(vs.styles[STYLE_DEFAULT].characterSet);
 }
 
-class CaseFolderUTF8 : public CaseFolderTable {
-public:
-       CaseFolderUTF8() {
-               StandardASCII();
-       }
-       virtual size_t Fold(char *folded, size_t sizeFolded, const char *mixed, size_t lenMixed) {
-               if ((lenMixed == 1) && (sizeFolded > 0)) {
-                       folded[0] = mapping[static_cast<unsigned char>(mixed[0])];
-                       return 1;
-               } else {
-                       gchar *mapped = g_utf8_casefold(mixed, lenMixed);
-                       size_t lenMapped = strlen(mapped);
-                       if (lenMapped < sizeFolded) {
-                               memcpy(folded, mapped,  lenMapped);
-                       } else {
-                               lenMapped = 0;
-                       }
-                       g_free(mapped);
-                       return lenMapped;
-               }
-       }
-};
-
 class CaseFolderDBCS : public CaseFolderTable {
        const char *charSet;
 public:
@@ -1301,11 +1251,10 @@ public:
                        folded[0] = mapping[static_cast<unsigned char>(mixed[0])];
                        return 1;
                } else if (*charSet) {
-                       int convertedLength = lenMixed;
-                       char *sUTF8 = ConvertText(&convertedLength, const_cast<char *>(mixed), lenMixed,
+                       std::string sUTF8 = ConvertText(mixed, lenMixed,
                                "UTF-8", charSet, false);
-                       if (sUTF8) {
-                               gchar *mapped = g_utf8_casefold(sUTF8, strlen(sUTF8));
+                       if (!sUTF8.empty()) {
+                               gchar *mapped = g_utf8_casefold(sUTF8.c_str(), sUTF8.length());
                                size_t lenMapped = strlen(mapped);
                                if (lenMapped < sizeFolded) {
                                        memcpy(folded, mapped,  lenMapped);
@@ -1314,7 +1263,6 @@ public:
                                        lenMapped = 1;
                                }
                                g_free(mapped);
-                               delete []sUTF8;
                                return lenMapped;
                        }
                }
@@ -1326,7 +1274,7 @@ public:
 
 CaseFolder *ScintillaGTK::CaseFolderForEncoding() {
        if (pdoc->dbcsCodePage == SC_CP_UTF8) {
-               return new CaseFolderUTF8();
+               return new CaseFolderUnicode();
        } else {
                const char *charSetBuffer = CharacterSetID();
                if (charSetBuffer) {
@@ -1337,23 +1285,20 @@ CaseFolder *ScintillaGTK::CaseFolderForEncoding() {
                                for (int i=0x80; i<0x100; i++) {
                                        char sCharacter[2] = "A";
                                        sCharacter[0] = i;
-                                       int convertedLength = 1;
-                                       const char *sUTF8 = ConvertText(&convertedLength, sCharacter, 1,
-                                               "UTF-8", charSetBuffer, false);
-                                       if (sUTF8) {
-                                               gchar *mapped = g_utf8_casefold(sUTF8, strlen(sUTF8));
+                                       // Silent as some bytes have no assigned character
+                                       std::string sUTF8 = ConvertText(sCharacter, 1,
+                                               "UTF-8", charSetBuffer, false, true);
+                                       if (!sUTF8.empty()) {
+                                               gchar *mapped = g_utf8_casefold(sUTF8.c_str(), 
sUTF8.length());
                                                if (mapped) {
-                                                       int mappedLength = strlen(mapped);
-                                                       const char *mappedBack = ConvertText(&mappedLength, 
mapped,
-                                                               mappedLength, charSetBuffer, "UTF-8", false, 
true);
-                                                       if (mappedBack && (strlen(mappedBack) == 1) && 
(mappedBack[0] != sCharacter[0])) {
+                                                       std::string mappedBack = ConvertText(mapped, 
strlen(mapped),
+                                                               charSetBuffer, "UTF-8", false, true);
+                                                       if ((mappedBack.length() == 1) && (mappedBack[0] != 
sCharacter[0])) {
                                                                pcf->SetTranslation(sCharacter[0], 
mappedBack[0]);
                                                        }
-                                                       delete []mappedBack;
                                                        g_free(mapped);
                                                }
                                        }
-                                       delete []sUTF8;
                                }
                                return pcf;
                        } else {
@@ -1364,50 +1309,48 @@ CaseFolder *ScintillaGTK::CaseFolderForEncoding() {
        }
 }
 
-std::string ScintillaGTK::CaseMapString(const std::string &s, int caseMapping) {
-       if (s.size() == 0)
-               return std::string();
-
-       if (caseMapping == cmSame)
-               return s;
+namespace {
 
-       const char *needsFree1 = 0;     // Must be freed with delete []
-       const char *charSetBuffer = CharacterSetID();
-       const char *sUTF8 = s.c_str();
-       int rangeBytes = s.size();
-
-       int convertedLength = rangeBytes;
-       // Change text to UTF-8
-       if (!IsUnicodeMode()) {
-               // Need to convert
-               if (*charSetBuffer) {
-                       sUTF8 = ConvertText(&convertedLength, const_cast<char *>(s.c_str()), rangeBytes,
-                               "UTF-8", charSetBuffer, false);
-                       needsFree1 = sUTF8;
+struct CaseMapper {
+       gchar *mapped;  // Must be freed with g_free
+       CaseMapper(const std::string &sUTF8, bool toUpperCase) {
+               if (toUpperCase) {
+                       mapped = g_utf8_strup(sUTF8.c_str(), sUTF8.length());
+               } else {
+                       mapped = g_utf8_strdown(sUTF8.c_str(), sUTF8.length());
                }
        }
-       gchar *mapped;  // Must be freed with g_free
-       if (caseMapping == cmUpper) {
-               mapped = g_utf8_strup(sUTF8, convertedLength);
-       } else {
-               mapped = g_utf8_strdown(sUTF8, convertedLength);
+       ~CaseMapper() {
+               g_free(mapped);
        }
-       int mappedLength = strlen(mapped);
-       char *mappedBack = mapped;
+};
 
-       char *needsFree2 = 0;   // Must be freed with delete []
-       if (!IsUnicodeMode()) {
-               if (*charSetBuffer) {
-                       mappedBack = ConvertText(&mappedLength, mapped, mappedLength, charSetBuffer, "UTF-8", 
false);
-                       needsFree2 = mappedBack;
-               }
+}
+
+std::string ScintillaGTK::CaseMapString(const std::string &s, int caseMapping) {
+       if ((s.size() == 0) || (caseMapping == cmSame))
+               return s;
+
+       if (IsUnicodeMode()) {
+               std::string retMapped(s.length() * maxExpansionCaseConversion, 0);
+               size_t lenMapped = CaseConvertString(&retMapped[0], retMapped.length(), s.c_str(), 
s.length(), 
+                       (caseMapping == cmUpper) ? CaseConversionUpper : CaseConversionLower);
+               retMapped.resize(lenMapped);
+               return retMapped;
        }
 
-       std::string ret(mappedBack, mappedLength);
-       g_free(mapped);
-       delete []needsFree1;
-       delete []needsFree2;
-       return ret;
+       const char *charSetBuffer = CharacterSetID();
+
+       if (!*charSetBuffer) {
+               CaseMapper mapper(s, caseMapping == cmUpper);
+               return std::string(mapper.mapped, strlen(mapper.mapped));
+       } else {
+               // Change text to UTF-8
+               std::string sUTF8 = ConvertText(s.c_str(), s.length(),
+                       "UTF-8", charSetBuffer, false);
+               CaseMapper mapper(sUTF8, caseMapping == cmUpper);
+               return ConvertText(mapper.mapped, strlen(mapper.mapped), charSetBuffer, "UTF-8", false);
+       }
 }
 
 int ScintillaGTK::KeyDefault(int key, int modifiers) {
@@ -1497,14 +1440,14 @@ void ScintillaGTK::ClaimSelection() {
                primarySelection = true;
                gtk_selection_owner_set(GTK_WIDGET(PWidget(wMain)),
                                        GDK_SELECTION_PRIMARY, GDK_CURRENT_TIME);
-               primary.Free();
+               primary.Clear();
        } else if (OwnPrimarySelection()) {
                primarySelection = true;
-               if (primary.s == NULL)
+               if (primary.Empty())
                        gtk_selection_owner_set(NULL, GDK_SELECTION_PRIMARY, GDK_CURRENT_TIME);
        } else {
                primarySelection = false;
-               primary.Free();
+               primary.Clear();
        }
 }
 
@@ -1528,9 +1471,7 @@ void ScintillaGTK::GetGtkSelectionText(GtkSelectionData *selectionData, Selectio
 
        // Return empty string if selection is not a string
        if ((selectionTypeData != GDK_TARGET_STRING) && (selectionTypeData != atomUTF8)) {
-               char *empty = new char[1];
-               empty[0] = '\0';
-               selText.Set(empty, 0, SC_CP_UTF8, 0, false, false);
+               selText.Clear();
                return;
        }
 
@@ -1544,29 +1485,26 @@ void ScintillaGTK::GetGtkSelectionText(GtkSelectionData *selectionData, Selectio
                len--;  // Forget the extra '\0'
 #endif
 
-       char *dest;
+       std::string dest = Document::TransformLineEnds(data, len, pdoc->eolMode);
        if (selectionTypeData == GDK_TARGET_STRING) {
-               dest = Document::TransformLineEnds(&len, data, len, pdoc->eolMode);
                if (IsUnicodeMode()) {
                        // Unknown encoding so assume in Latin1
-                       char *destPrevious = dest;
-                       dest = UTF8FromLatin1(dest, len);
-                       selText.Set(dest, len, SC_CP_UTF8, 0, selText.rectangular, false);
-                       delete []destPrevious;
+                       dest = UTF8FromLatin1(dest.c_str(), dest.length());
+                       selText.Copy(dest, SC_CP_UTF8, 0, isRectangular, false);
                } else {
                        // Assume buffer is in same encoding as selection
-                       selText.Set(dest, len, pdoc->dbcsCodePage,
+                       selText.Copy(dest, pdoc->dbcsCodePage,
                                vs.styles[STYLE_DEFAULT].characterSet, isRectangular, false);
                }
        } else {        // UTF-8
-               dest = Document::TransformLineEnds(&len, data, len, pdoc->eolMode);
-               selText.Set(dest, len, SC_CP_UTF8, 0, isRectangular, false);
                const char *charSetBuffer = CharacterSetID();
                if (!IsUnicodeMode() && *charSetBuffer) {
                        // Convert to locale
-                       dest = ConvertText(&len, selText.s, selText.len, charSetBuffer, "UTF-8", true);
-                       selText.Set(dest, len, pdoc->dbcsCodePage,
-                               vs.styles[STYLE_DEFAULT].characterSet, selText.rectangular, false);
+                       dest = ConvertText(dest.c_str(), dest.length(), charSetBuffer, "UTF-8", true);
+                       selText.Copy(dest, pdoc->dbcsCodePage,
+                               vs.styles[STYLE_DEFAULT].characterSet, isRectangular, false);
+               } else {
+                       selText.Copy(dest, SC_CP_UTF8, 0, isRectangular, false);
                }
        }
 }
@@ -1593,9 +1531,9 @@ void ScintillaGTK::ReceivedSelection(GtkSelectionData *selection_data) {
                                        sel.Range(sel.Main()).Start();
 
                                if (selText.rectangular) {
-                                       PasteRectangular(selStart, selText.s, selText.len);
+                                       PasteRectangular(selStart, selText.Data(), selText.Length());
                                } else {
-                                       InsertPaste(selStart, selText.s, selText.len);
+                                       InsertPaste(selStart, selText.Data(), selText.Length());
                                }
                                EnsureCaretVisible();
                        }
@@ -1611,16 +1549,15 @@ void ScintillaGTK::ReceivedSelection(GtkSelectionData *selection_data) {
 void ScintillaGTK::ReceivedDrop(GtkSelectionData *selection_data) {
        dragWasDropped = true;
        if (TypeOfGSD(selection_data) == atomUriList || TypeOfGSD(selection_data) == atomDROPFILES_DND) {
-               char *ptr = new char[LengthOfGSD(selection_data) + 1];
-               ptr[LengthOfGSD(selection_data)] = '\0';
-               memcpy(ptr, DataOfGSD(selection_data), LengthOfGSD(selection_data));
-               NotifyURIDropped(ptr);
-               delete []ptr;
+               const char *data = reinterpret_cast<const char *>(DataOfGSD(selection_data));
+               std::vector<char> drop(data, data + LengthOfGSD(selection_data));
+               drop.push_back('\0');
+               NotifyURIDropped(&drop[0]);
        } else if ((TypeOfGSD(selection_data) == GDK_TARGET_STRING) || (TypeOfGSD(selection_data) == 
atomUTF8)) {
                if (TypeOfGSD(selection_data) > 0) {
                        SelectionText selText;
                        GetGtkSelectionText(selection_data, selText);
-                       DropAt(posDrop, selText.s, false, selText.rectangular);
+                       DropAt(posDrop, selText.Data(), selText.Length(), false, selText.rectangular);
                }
        } else if (LengthOfGSD(selection_data) > 0) {
                //~ fprintf(stderr, "ReceivedDrop other %p\n", static_cast<void *>(selection_data->type));
@@ -1637,10 +1574,9 @@ void ScintillaGTK::GetSelection(GtkSelectionData *selection_data, guint info, Se
        // from code below
        SelectionText *newline_normalized = NULL;
        {
-               int tmpstr_len;
-               char *tmpstr = Document::TransformLineEnds(&tmpstr_len, text->s, text->len, SC_EOL_LF);
+               std::string tmpstr = Document::TransformLineEnds(text->Data(), text->Length(), SC_EOL_LF);
                newline_normalized = new SelectionText();
-               newline_normalized->Set(tmpstr, tmpstr_len, SC_CP_UTF8, 0, text->rectangular, false);
+               newline_normalized->Copy(tmpstr, SC_CP_UTF8, 0, text->rectangular, false);
                text = newline_normalized;
        }
 #endif
@@ -1650,10 +1586,9 @@ void ScintillaGTK::GetSelection(GtkSelectionData *selection_data, guint info, Se
        if ((text->codePage != SC_CP_UTF8) && (info == TARGET_UTF8_STRING)) {
                const char *charSet = ::CharacterSetID(text->characterSet);
                if (*charSet) {
-                       int new_len;
-                       char* tmputf = ConvertText(&new_len, text->s, text->len, "UTF-8", charSet, false);
+                       std::string tmputf = ConvertText(text->Data(), text->Length(), "UTF-8", charSet, 
false);
                        converted = new SelectionText();
-                       converted->Set(tmputf, new_len, SC_CP_UTF8, 0, text->rectangular, false);
+                       converted->Copy(tmputf, SC_CP_UTF8, 0, text->rectangular, false);
                        text = converted;
                }
        }
@@ -1665,8 +1600,8 @@ void ScintillaGTK::GetSelection(GtkSelectionData *selection_data, guint info, Se
        // All other tested aplications behave benignly by ignoring the \0.
        // The #if is here because on Windows cfColumnSelect clip entry is used
        // instead as standard indicator of rectangularness (so no need to kludge)
-       const char *textData = text->s ? text->s : "";
-       int len = strlen(textData);
+       const char *textData = text->Data();
+       int len = text->Length();
 #if PLAT_GTK_WIN32 == 0
        if (text->rectangular)
                len++;
@@ -1713,7 +1648,7 @@ void ScintillaGTK::UnclaimSelection(GdkEventSelection *selection_event) {
                if (selection_event->selection == GDK_SELECTION_PRIMARY) {
                        //Platform::DebugPrintf("UnclaimPrimarySelection\n");
                        if (!OwnPrimarySelection()) {
-                               primary.Free();
+                               primary.Clear();
                                primarySelection = false;
                                FullPaint();
                        }
@@ -1731,44 +1666,41 @@ void ScintillaGTK::Resize(int width, int height) {
 #if GTK_CHECK_VERSION(3,0,0)
        GtkRequisition requisition;
        gtk_widget_get_requisition(PWidget(scrollbarv), &requisition);
-       scrollBarWidth = requisition.width;
+       verticalScrollBarWidth = requisition.width;
        gtk_widget_get_requisition(PWidget(scrollbarh), &requisition);
-       scrollBarHeight = requisition.height;
+       horizontalScrollBarHeight = requisition.height;
 #else
-       scrollBarWidth = GTK_WIDGET(PWidget(scrollbarv))->requisition.width;
-       scrollBarHeight = GTK_WIDGET(PWidget(scrollbarh))->requisition.height;
+       verticalScrollBarWidth = GTK_WIDGET(PWidget(scrollbarv))->requisition.width;
+       horizontalScrollBarHeight = GTK_WIDGET(PWidget(scrollbarh))->requisition.height;
 #endif
 
        // These allocations should never produce negative sizes as they would wrap around to huge
        // unsigned numbers inside GTK+ causing warnings.
        bool showSBHorizontal = horizontalScrollBarVisible && (wrapState == eWrapNone);
-       int horizontalScrollBarHeight = scrollBarHeight;
-       if (!showSBHorizontal)
-               horizontalScrollBarHeight = 0;
 
        GtkAllocation alloc;
        if (showSBHorizontal) {
                gtk_widget_show(GTK_WIDGET(PWidget(scrollbarh)));
                alloc.x = 0;
-               alloc.y = height - scrollBarHeight;
-               alloc.width = Platform::Maximum(1, width - scrollBarWidth);
+               alloc.y = height - horizontalScrollBarHeight;
+               alloc.width = Platform::Maximum(1, width - verticalScrollBarWidth);
                alloc.height = horizontalScrollBarHeight;
                gtk_widget_size_allocate(GTK_WIDGET(PWidget(scrollbarh)), &alloc);
        } else {
                gtk_widget_hide(GTK_WIDGET(PWidget(scrollbarh)));
+               horizontalScrollBarHeight = 0; // in case horizontalScrollBarVisible is true.
        }
 
        if (verticalScrollBarVisible) {
                gtk_widget_show(GTK_WIDGET(PWidget(scrollbarv)));
-               alloc.x = width - scrollBarWidth;
+               alloc.x = width - verticalScrollBarWidth;
                alloc.y = 0;
-               alloc.width = scrollBarWidth;
-               alloc.height = Platform::Maximum(1, height - scrollBarHeight);
-               if (!showSBHorizontal)
-                       alloc.height += scrollBarWidth-1;
+               alloc.width = verticalScrollBarWidth;
+               alloc.height = Platform::Maximum(1, height - horizontalScrollBarHeight);
                gtk_widget_size_allocate(GTK_WIDGET(PWidget(scrollbarv)), &alloc);
        } else {
                gtk_widget_hide(GTK_WIDGET(PWidget(scrollbarv)));
+               verticalScrollBarWidth = 0;
        }
        if (IS_WIDGET_MAPPED(PWidget(wMain))) {
                ChangeSize();
@@ -1776,12 +1708,8 @@ void ScintillaGTK::Resize(int width, int height) {
 
        alloc.x = 0;
        alloc.y = 0;
-       alloc.width = Platform::Maximum(1, width - scrollBarWidth);
-       alloc.height = Platform::Maximum(1, height - scrollBarHeight);
-       if (!showSBHorizontal)
-               alloc.height += scrollBarHeight;
-       if (!verticalScrollBarVisible)
-               alloc.width += scrollBarWidth;
+       alloc.width = Platform::Maximum(1, width - verticalScrollBarWidth);
+       alloc.height = Platform::Maximum(1, height - horizontalScrollBarHeight);
        gtk_widget_size_allocate(GTK_WIDGET(PWidget(wText)), &alloc);
 }
 
@@ -1824,7 +1752,11 @@ gint ScintillaGTK::PressThis(GdkEventButton *event) {
                if (event->type != GDK_BUTTON_PRESS)
                        return FALSE;
 
-               evbtn = *event;
+               if (evbtn) {
+                       gdk_event_free(reinterpret_cast<GdkEvent *>(evbtn));
+                       evbtn = 0;
+               }
+               evbtn = reinterpret_cast<GdkEventButton *>(gdk_event_copy(reinterpret_cast<GdkEvent 
*>(event)));
                Point pt;
                pt.x = int(event->x);
                pt.y = int(event->y);
@@ -1850,7 +1782,7 @@ gint ScintillaGTK::PressThis(GdkEventButton *event) {
                } else if (event->button == 2) {
                        // Grab the primary selection if it exists
                        SelectionPosition pos = SPositionFromLocation(pt, false, false, UserVirtualSpace());
-                       if (OwnPrimarySelection() && primary.s == NULL)
+                       if (OwnPrimarySelection() && primary.Empty())
                                CopySelectionRange(&primary);
 
                        sel.Clear();
@@ -1923,8 +1855,7 @@ gint ScintillaGTK::MouseRelease(GtkWidget *widget, GdkEventButton *event) {
 
 // win32gtk and GTK >= 2 use SCROLL_* events instead of passing the
 // button4/5/6/7 events to the GTK app
-gint ScintillaGTK::ScrollEvent(GtkWidget *widget,
-                               GdkEventScroll *event) {
+gint ScintillaGTK::ScrollEvent(GtkWidget *widget, GdkEventScroll *event) {
        ScintillaGTK *sciThis = ScintillaFromWidget(widget);
        try {
 
@@ -2597,7 +2528,7 @@ void ScintillaGTK::SelectionGet(GtkWidget *widget,
        try {
                //Platform::DebugPrintf("Selection get\n");
                if (SelectionOfGSD(selection_data) == GDK_SELECTION_PRIMARY) {
-                       if (sciThis->primary.s == NULL) {
+                       if (sciThis->primary.Empty()) {
                                sciThis->CopySelectionRange(&sciThis->primary);
                        }
                        sciThis->GetSelection(selection_data, info, &sciThis->primary);
@@ -2617,10 +2548,6 @@ gint ScintillaGTK::SelectionClear(GtkWidget *widget, GdkEventSelection *selectio
        return TRUE;
 }
 
-void ScintillaGTK::DragBegin(GtkWidget *, GdkDragContext *) {
-       //Platform::DebugPrintf("DragBegin\n");
-}
-
 gboolean ScintillaGTK::DragMotionThis(GdkDragContext *context,
                                  gint x, gint y, guint dragtime) {
        try {
@@ -2998,7 +2925,10 @@ static void scintilla_init(ScintillaObject *sci) {
 }
 
 GtkWidget* scintilla_new() {
-       return GTK_WIDGET(g_object_new(scintilla_get_type(), NULL));
+       GtkWidget *widget = GTK_WIDGET(g_object_new(scintilla_get_type(), NULL));
+       gtk_widget_set_direction(widget, GTK_TEXT_DIR_LTR);
+
+       return widget;
 }
 
 void scintilla_set_id(ScintillaObject *sci, uptr_t id) {
diff --git a/plugins/scintilla/scintilla/include/ILexer.h b/plugins/scintilla/scintilla/include/ILexer.h
index 1260c13..e93de81 100644
--- a/plugins/scintilla/scintilla/include/ILexer.h
+++ b/plugins/scintilla/scintilla/include/ILexer.h
@@ -48,6 +48,8 @@ public:
 class IDocumentWithLineEnd : public IDocument {
 public:
        virtual int SCI_METHOD LineEnd(int line) const = 0;
+       virtual int SCI_METHOD GetRelativePosition(int positionStart, int characterOffset) const = 0;
+       virtual int SCI_METHOD GetCharacterAndWidth(int position, int *pWidth) const = 0;
 };
 
 enum { lvOriginal=0, lvSubStyles=1 };
diff --git a/plugins/scintilla/scintilla/include/Platform.h b/plugins/scintilla/scintilla/include/Platform.h
index 70a9ccc..311b1c4 100644
--- a/plugins/scintilla/scintilla/include/Platform.h
+++ b/plugins/scintilla/scintilla/include/Platform.h
@@ -13,6 +13,7 @@
 // PLAT_GTK_WIN32 is defined additionally when running PLAT_GTK under Win32
 // PLAT_WIN = Win32 API on Win32 OS
 // PLAT_WX is wxWindows on any supported platform
+// PLAT_TK = Tcl/TK on Linux or Win32
 
 #define PLAT_GTK 0
 #define PLAT_GTK_WIN32 0
@@ -22,7 +23,8 @@
 #define PLAT_WX  0
 #define PLAT_QT 0
 #define PLAT_FOX 0
-#define PLAT_NCURSES 0
+#define PLAT_CURSES 0
+#define PLAT_TK 0
 
 #if defined(FOX)
 #undef PLAT_FOX
@@ -32,14 +34,18 @@
 #undef PLAT_WX
 #define PLAT_WX  1
 
-#elif defined(NCURSES)
-#undef PLAT_NCURSES
-#define PLAT_NCURSES 1
+#elif defined(CURSES)
+#undef PLAT_CURSES
+#define PLAT_CURSES 1
 
 #elif defined(SCINTILLA_QT)
 #undef PLAT_QT
 #define PLAT_QT 1
 
+#elif defined(TK)
+#undef PLAT_TK
+#define PLAT_TK 1
+
 #elif defined(GTK)
 #undef PLAT_GTK
 #define PLAT_GTK 1
@@ -119,19 +125,19 @@ public:
 
        // Other automatically defined methods (assignment, copy constructor, destructor) are fine
 
-       bool operator==(PRectangle &rc) {
+       bool operator==(PRectangle &rc) const {
                return (rc.left == left) && (rc.right == right) &&
                        (rc.top == top) && (rc.bottom == bottom);
        }
-       bool Contains(Point pt) {
+       bool Contains(Point pt) const {
                return (pt.x >= left) && (pt.x <= right) &&
                        (pt.y >= top) && (pt.y <= bottom);
        }
-       bool Contains(PRectangle rc) {
+       bool Contains(PRectangle rc) const {
                return (rc.left >= left) && (rc.right <= right) &&
                        (rc.top >= top) && (rc.bottom <= bottom);
        }
-       bool Intersects(PRectangle other) {
+       bool Intersects(PRectangle other) const {
                return (right > other.left) && (left < other.right) &&
                        (bottom > other.top) && (top < other.bottom);
        }
@@ -141,9 +147,9 @@ public:
                right += xDelta;
                bottom += yDelta;
        }
-       XYPOSITION Width() { return right - left; }
-       XYPOSITION Height() { return bottom - top; }
-       bool Empty() {
+       XYPOSITION Width() const { return right - left; }
+       XYPOSITION Height() const { return bottom - top; }
+       bool Empty() const {
                return (Height() <= 0) || (Width() <= 0);
        }
 };
@@ -199,15 +205,15 @@ public:
                return co;
        }
 
-       unsigned int GetRed() {
+       unsigned int GetRed() const {
                return co & 0xff;
        }
 
-       unsigned int GetGreen() {
+       unsigned int GetGreen() const {
                return (co >> 8) & 0xff;
        }
 
-       unsigned int GetBlue() {
+       unsigned int GetBlue() const {
                return (co >> 16) & 0xff;
        }
 };
diff --git a/plugins/scintilla/scintilla/include/SciLexer.h b/plugins/scintilla/scintilla/include/SciLexer.h
index 44043fe..18cdb98 100644
--- a/plugins/scintilla/scintilla/include/SciLexer.h
+++ b/plugins/scintilla/scintilla/include/SciLexer.h
@@ -120,6 +120,8 @@
 #define SCLEX_ECL 105
 #define SCLEX_OSCRIPT 106
 #define SCLEX_VISUALPROLOG 107
+#define SCLEX_LITERATEHASKELL 108
+#define SCLEX_STTXT 109
 #define SCLEX_AUTOMATIC 1000
 #define SCE_P_DEFAULT 0
 #define SCE_P_COMMENTLINE 1
@@ -161,6 +163,7 @@
 #define SCE_C_TRIPLEVERBATIM 21
 #define SCE_C_HASHQUOTEDSTRING 22
 #define SCE_C_PREPROCESSORCOMMENT 23
+#define SCE_C_PREPROCESSORCOMMENTDOC 24
 #define SCE_D_DEFAULT 0
 #define SCE_D_COMMENT 1
 #define SCE_D_COMMENTLINE 2
@@ -1020,6 +1023,12 @@
 #define SCE_HA_COMMENTBLOCK 14
 #define SCE_HA_COMMENTBLOCK2 15
 #define SCE_HA_COMMENTBLOCK3 16
+#define SCE_HA_PRAGMA 17
+#define SCE_HA_PREPROCESSOR 18
+#define SCE_HA_STRINGEOL 19
+#define SCE_HA_RESERVED_OPERATOR 20
+#define SCE_HA_LITERATE_COMMENT 21
+#define SCE_HA_LITERATE_CODEDELIM 22
 #define SCE_T3_DEFAULT 0
 #define SCE_T3_X_DEFAULT 1
 #define SCE_T3_PREPROCESSOR 2
@@ -1324,6 +1333,9 @@
 #define SCE_POWERSHELL_FUNCTION 11
 #define SCE_POWERSHELL_USER1 12
 #define SCE_POWERSHELL_COMMENTSTREAM 13
+#define SCE_POWERSHELL_HERE_STRING 14
+#define SCE_POWERSHELL_HERE_CHARACTER 15
+#define SCE_POWERSHELL_COMMENTDOCKEYWORD 16
 #define SCE_MYSQL_DEFAULT 0
 #define SCE_MYSQL_COMMENT 1
 #define SCE_MYSQL_COMMENTLINE 2
@@ -1616,6 +1628,25 @@
 #define SCE_VISUALPROLOG_STRING_VERBATIM 20
 #define SCE_VISUALPROLOG_STRING_VERBATIM_SPECIAL 21
 #define SCE_VISUALPROLOG_STRING_VERBATIM_EOL 22
+#define SCE_STTXT_DEFAULT 0
+#define SCE_STTXT_COMMENT 1
+#define SCE_STTXT_COMMENTLINE 2
+#define SCE_STTXT_KEYWORD 3
+#define SCE_STTXT_TYPE 4
+#define SCE_STTXT_FUNCTION 5
+#define SCE_STTXT_FB 6
+#define SCE_STTXT_NUMBER 7
+#define SCE_STTXT_HEXNUMBER 8
+#define SCE_STTXT_PRAGMA 9
+#define SCE_STTXT_OPERATOR 10
+#define SCE_STTXT_CHARACTER 11
+#define SCE_STTXT_STRING1 12
+#define SCE_STTXT_STRING2 13
+#define SCE_STTXT_STRINGEOL 14
+#define SCE_STTXT_IDENTIFIER 15
+#define SCE_STTXT_DATETIME 16
+#define SCE_STTXT_VARS 17
+#define SCE_STTXT_PRAGMAS 18
 /* --Autogenerated -- end of section automatically generated from Scintilla.iface */
 
 #endif
diff --git a/plugins/scintilla/scintilla/include/Scintilla.h b/plugins/scintilla/scintilla/include/Scintilla.h
index dabab00..a229e4c 100644
--- a/plugins/scintilla/scintilla/include/Scintilla.h
+++ b/plugins/scintilla/scintilla/include/Scintilla.h
@@ -270,6 +270,7 @@ typedef sptr_t (*SciFnDirect)(sptr_t ptr, unsigned int iMessage, uptr_t wParam,
 #define INDIC_SQUIGGLELOW 11
 #define INDIC_DOTBOX 12
 #define INDIC_SQUIGGLEPIXMAP 13
+#define INDIC_COMPOSITIONTHICK 14
 #define INDIC_MAX 31
 #define INDIC_CONTAINER 8
 #define INDIC0_MASK 0x20
@@ -446,7 +447,19 @@ typedef sptr_t (*SciFnDirect)(sptr_t ptr, unsigned int iMessage, uptr_t wParam,
 #define SCI_SETFOLDEXPANDED 2229
 #define SCI_GETFOLDEXPANDED 2230
 #define SCI_TOGGLEFOLD 2231
+#define SC_FOLDACTION_CONTRACT 0
+#define SC_FOLDACTION_EXPAND 1
+#define SC_FOLDACTION_TOGGLE 2
+#define SCI_FOLDLINE 2237
+#define SCI_FOLDCHILDREN 2238
+#define SCI_EXPANDCHILDREN 2239
+#define SCI_FOLDALL 2662
 #define SCI_ENSUREVISIBLE 2232
+#define SC_AUTOMATICFOLD_SHOW 0x0001
+#define SC_AUTOMATICFOLD_CLICK 0x0002
+#define SC_AUTOMATICFOLD_CHANGE 0x0004
+#define SCI_SETAUTOMATICFOLD 2663
+#define SCI_GETAUTOMATICFOLD 2664
 #define SC_FOLDFLAG_LINEBEFORE_EXPANDED 0x0002
 #define SC_FOLDFLAG_LINEBEFORE_CONTRACTED 0x0004
 #define SC_FOLDFLAG_LINEAFTER_EXPANDED 0x0008
@@ -704,6 +717,11 @@ typedef sptr_t (*SciFnDirect)(sptr_t ptr, unsigned int iMessage, uptr_t wParam,
 #define SC_CASEINSENSITIVEBEHAVIOUR_IGNORECASE 1
 #define SCI_AUTOCSETCASEINSENSITIVEBEHAVIOUR 2634
 #define SCI_AUTOCGETCASEINSENSITIVEBEHAVIOUR 2635
+#define SC_ORDER_PRESORTED 0
+#define SC_ORDER_PERFORMSORT 1
+#define SC_ORDER_CUSTOM 2
+#define SCI_AUTOCSETORDER 2660
+#define SCI_AUTOCGETORDER 2661
 #define SCI_ALLOCATE 2446
 #define SCI_TARGETASUTF8 2447
 #define SCI_SETLENGTHFORENCODE 2448
diff --git a/plugins/scintilla/scintilla/include/Scintilla.iface 
b/plugins/scintilla/scintilla/include/Scintilla.iface
index 496f472..120a543 100644
--- a/plugins/scintilla/scintilla/include/Scintilla.iface
+++ b/plugins/scintilla/scintilla/include/Scintilla.iface
@@ -581,6 +581,7 @@ val INDIC_DOTS=10
 val INDIC_SQUIGGLELOW=11
 val INDIC_DOTBOX=12
 val INDIC_SQUIGGLEPIXMAP=13
+val INDIC_COMPOSITIONTHICK=14
 val INDIC_MAX=31
 val INDIC_CONTAINER=8
 val INDIC0_MASK=0x20
@@ -1109,9 +1110,37 @@ get bool GetFoldExpanded=2230(int line,)
 # Switch a header line between expanded and contracted.
 fun void ToggleFold=2231(int line,)
 
+enu FoldAction=SC_FOLDACTION
+val SC_FOLDACTION_CONTRACT=0
+val SC_FOLDACTION_EXPAND=1
+val SC_FOLDACTION_TOGGLE=2
+
+# Expand or contract a fold header.
+fun void FoldLine=2237(int line, int action)
+
+# Expand or contract a fold header and its children.
+fun void FoldChildren=2238(int line, int action)
+
+# Expand a fold header and all children. Use the level argument instead of the line's current level.
+fun void ExpandChildren=2239(int line, int level)
+
+# Expand or contract all fold headers.
+fun void FoldAll=2662(int action,)
+
 # Ensure a particular line is visible by expanding any header line hiding it.
 fun void EnsureVisible=2232(int line,)
 
+enu AutomaticFold=SC_AUTOMATICFOLD_
+val SC_AUTOMATICFOLD_SHOW=0x0001
+val SC_AUTOMATICFOLD_CLICK=0x0002
+val SC_AUTOMATICFOLD_CHANGE=0x0004
+
+# Set automatic folding behaviours.
+set void SetAutomaticFold=2663(int automaticFold,)
+
+# Get automatic folding behaviours.
+get int GetAutomaticFold=2664(,)
+
 enu FoldFlag=SC_FOLDFLAG_
 val SC_FOLDFLAG_LINEBEFORE_EXPANDED=0x0002
 val SC_FOLDFLAG_LINEBEFORE_CONTRACTED=0x0004
@@ -1842,6 +1871,17 @@ set void AutoCSetCaseInsensitiveBehaviour=2634(int behaviour,)
 # Get auto-completion case insensitive behaviour.
 get int AutoCGetCaseInsensitiveBehaviour=2635(,)
 
+enu Ordering=SC_ORDER_
+val SC_ORDER_PRESORTED=0
+val SC_ORDER_PERFORMSORT=1
+val SC_ORDER_CUSTOM=2
+
+# Set the way autocompletion lists are ordered.
+set void AutoCSetOrder=2660(int order,)
+
+# Get the way autocompletion lists are ordered.
+get int AutoCGetOrder=2661(,)
+
 # Enlarge the document to a particular size of text bytes.
 fun void Allocate=2446(int bytes,)
 
@@ -2538,6 +2578,8 @@ val SCLEX_AVS=104
 val SCLEX_ECL=105
 val SCLEX_OSCRIPT=106
 val SCLEX_VISUALPROLOG=107
+val SCLEX_LITERATEHASKELL=108
+val SCLEX_STTXT=109
 
 # When a lexer specifies its language as SCLEX_AUTOMATIC it receives a
 # value assigned in sequence from SCLEX_AUTOMATIC+1.
@@ -2588,6 +2630,7 @@ val SCE_C_STRINGRAW=20
 val SCE_C_TRIPLEVERBATIM=21
 val SCE_C_HASHQUOTEDSTRING=22
 val SCE_C_PREPROCESSORCOMMENT=23
+val SCE_C_PREPROCESSORCOMMENTDOC=24
 # Lexical states for SCLEX_D
 lex D=SCLEX_D SCE_D_
 val SCE_D_DEFAULT=0
@@ -3570,6 +3613,12 @@ val SCE_HA_COMMENTLINE=13
 val SCE_HA_COMMENTBLOCK=14
 val SCE_HA_COMMENTBLOCK2=15
 val SCE_HA_COMMENTBLOCK3=16
+val SCE_HA_PRAGMA=17
+val SCE_HA_PREPROCESSOR=18
+val SCE_HA_STRINGEOL=19
+val SCE_HA_RESERVED_OPERATOR=20
+val SCE_HA_LITERATE_COMMENT=21
+val SCE_HA_LITERATE_CODEDELIM=22
 # Lexical states of SCLEX_TADS3
 lex TADS3=SCLEX_TADS3 SCE_T3_
 val SCE_T3_DEFAULT=0
@@ -3910,6 +3959,9 @@ val SCE_POWERSHELL_ALIAS=10
 val SCE_POWERSHELL_FUNCTION=11
 val SCE_POWERSHELL_USER1=12
 val SCE_POWERSHELL_COMMENTSTREAM=13
+val SCE_POWERSHELL_HERE_STRING=14
+val SCE_POWERSHELL_HERE_CHARACTER=15
+val SCE_POWERSHELL_COMMENTDOCKEYWORD=16
 # Lexical state for SCLEX_MYSQL
 lex MySQL=SCLEX_MYSQL SCE_MYSQL_
 val SCE_MYSQL_DEFAULT=0
@@ -4232,6 +4284,27 @@ val SCE_VISUALPROLOG_STRING_EOL_OPEN=19
 val SCE_VISUALPROLOG_STRING_VERBATIM=20
 val SCE_VISUALPROLOG_STRING_VERBATIM_SPECIAL=21
 val SCE_VISUALPROLOG_STRING_VERBATIM_EOL=22
+# Lexical states for SCLEX_STTXT
+lex StructuredText=SCLEX_STTXT SCE_STTXT_
+val SCE_STTXT_DEFAULT=0
+val SCE_STTXT_COMMENT=1
+val SCE_STTXT_COMMENTLINE=2
+val SCE_STTXT_KEYWORD=3
+val SCE_STTXT_TYPE=4
+val SCE_STTXT_FUNCTION=5
+val SCE_STTXT_FB=6
+val SCE_STTXT_NUMBER=7
+val SCE_STTXT_HEXNUMBER=8
+val SCE_STTXT_PRAGMA=9
+val SCE_STTXT_OPERATOR=10
+val SCE_STTXT_CHARACTER=11
+val SCE_STTXT_STRING1=12
+val SCE_STTXT_STRING2=13
+val SCE_STTXT_STRINGEOL=14
+val SCE_STTXT_IDENTIFIER=15
+val SCE_STTXT_DATETIME=16
+val SCE_STTXT_VARS=17
+val SCE_STTXT_PRAGMAS=18
 
 # Events
 
diff --git a/plugins/scintilla/scintilla/lexers.make b/plugins/scintilla/scintilla/lexers.make
index 9e26f46..1522e44 100644
--- a/plugins/scintilla/scintilla/lexers.make
+++ b/plugins/scintilla/scintilla/lexers.make
@@ -77,6 +77,7 @@ LEXER_OBJS = \
        lexers/LexSpecman.o\
        lexers/LexSpice.o\
        lexers/LexSQL.o\
+       lexers/LexSTTXT.o\
        lexers/LexTACL.o\
        lexers/LexTADS3.o\
        lexers/LexTAL.o\
@@ -168,6 +169,7 @@ LEXER_SRCS = \
        lexers/LexSpecman.cxx\
        lexers/LexSpice.cxx\
        lexers/LexSQL.cxx\
+       lexers/LexSTTXT.cxx\
        lexers/LexTACL.cxx\
        lexers/LexTADS3.cxx\
        lexers/LexTAL.cxx\
diff --git a/plugins/scintilla/scintilla/lexers/LexA68k.cxx b/plugins/scintilla/scintilla/lexers/LexA68k.cxx
index 970e429..0b60019 100644
--- a/plugins/scintilla/scintilla/lexers/LexA68k.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexA68k.cxx
@@ -117,13 +117,20 @@ static inline bool IsDoxygenChar (const int ch)
 
 static void ColouriseA68kDoc (unsigned int startPos, int length, int initStyle, WordList *keywordlists[], 
Accessor &styler)
 {
+    // Used to buffer a string, to be able to compare it using built-in functions 
+    char Buffer[100]; 
+ 
+ 
+    // Used to know the length of an operator 
+    int OpType; 
+ 
 
     // Get references to keywords lists
     WordList &cpuInstruction = *keywordlists[0];
     WordList &registers = *keywordlists[1];
     WordList &directive = *keywordlists[2];
     WordList &extInstruction = *keywordlists[3];
-    WordList &commentSpecial = *keywordlists[4];
+    WordList &alert          = *keywordlists[4]; 
     WordList &doxygenKeyword = *keywordlists[5];
 
 
@@ -133,103 +140,109 @@ static void ColouriseA68kDoc (unsigned int startPos, int length, int initStyle,
 
     /************************************************************
     *
-    *   Parse the text
+    *   Parse the source 
     *
     ************************************************************/
 
     for ( ; sc.More(); sc.Forward())
     {
-        char Buffer[100];
-        int OpType;
-
-        // Reset style at beginning of line
-        if (sc.atLineStart)
+        /************************************************************ 
+        * 
+        *   A style always terminates at the end of a line, even for 
+        *   comments (no multi-lines comments) 
+        * 
+        ************************************************************/ 
+        if (sc.atLineStart) { 
             sc.SetState(SCE_A68K_DEFAULT);
+        } 
 
 
         /************************************************************
         *
-        *   Handle current state if we are not in the "default style"
+        *   If we are not in "default style", check if the style continues 
+        *   In this case, we just have to loop 
         *
         ************************************************************/
 
         if (sc.state != SCE_A68K_DEFAULT)
         {
-            // Check if current style continue.
-            // If this case, we loop because there is nothing else to do
-            if (((sc.state == SCE_A68K_NUMBER_DEC) && isdigit(sc.ch))                                       
// Decimal number
+            if (   ((sc.state == SCE_A68K_NUMBER_DEC)        && isdigit(sc.ch))                      // 
Decimal number 
                 || ((sc.state == SCE_A68K_NUMBER_BIN) && IsBin(sc.ch))                                      
// Binary number
                 || ((sc.state == SCE_A68K_NUMBER_HEX) && isxdigit(sc.ch))                                   
// Hexa number
-                || ((sc.state == SCE_A68K_MACRO_ARG)  && isdigit(sc.ch))                                    
// Arg of macro
+                || ((sc.state == SCE_A68K_MACRO_ARG)         && isdigit(sc.ch))                      // 
Macro argument 
                 || ((sc.state == SCE_A68K_STRING1)    && (sc.ch != '\''))                                   
// String single-quoted
                 || ((sc.state == SCE_A68K_STRING2)    && (sc.ch != '\"'))                                   
// String double-quoted
-                || ((sc.state == SCE_A68K_MACRO_ARG)  && isdigit(sc.ch))                                    
// Macro argument
-                // Label. ' ' and '\t' are needed to handle macro declarations
-                || ((sc.state == SCE_A68K_LABEL)      && (sc.ch != ':') && (sc.ch != ' ') && (sc.ch != '\t'))
-                || ((sc.state == SCE_A68K_IDENTIFIER) && (sc.ch < 0x80) && IsIdentifierChar(sc.ch))         
// Identifier
-                || ((sc.state == SCE_A68K_COMMENT_DOXYGEN) && (sc.ch < 0x80) && IsDoxygenChar(sc.ch))       
// Doxygen keyword
-                || ((sc.state == SCE_A68K_COMMENT_WORD) && (sc.ch < 0x80) && isalpha(sc.ch)))               
// Comment current word
+                || ((sc.state == SCE_A68K_MACRO_DECLARATION) && IsIdentifierChar(sc.ch))             // 
Macro declaration (or global label, we don't know at this point) 
+                || ((sc.state == SCE_A68K_IDENTIFIER)        && IsIdentifierChar(sc.ch))             // 
Identifier 
+                || ((sc.state == SCE_A68K_LABEL)             && IsIdentifierChar(sc.ch))             // 
Label (local) 
+                || ((sc.state == SCE_A68K_COMMENT_DOXYGEN)   && IsDoxygenChar(sc.ch))                // 
Doxygen keyword 
+                || ((sc.state == SCE_A68K_COMMENT_SPECIAL)   && isalpha(sc.ch))                      // 
Alert 
+                || ((sc.state == SCE_A68K_COMMENT)           && !isalpha(sc.ch) && (sc.ch != '\\'))) // 
Normal comment 
             {
                 continue;
             }
 
-            // Check if some states terminate at the current char:
-            // we must include this char in the current style context
-            else if (((sc.state == SCE_A68K_STRING1)    && (sc.ch < 0x80) && (sc.ch == '\''))       // 
String single-quoted
-                     || ((sc.state == SCE_A68K_STRING2) && (sc.ch < 0x80) && (sc.ch == '\"'))       // 
String double-quoted
-                     || ((sc.state == SCE_A68K_LABEL)   && (sc.ch < 0x80) && (sc.ch == ':')))       // Label
-            {
-                sc.ForwardSetState(SCE_A68K_DEFAULT);
-            }
+        /************************************************************ 
+        * 
+        *   Check if current state terminates 
+        * 
+        ************************************************************/ 
 
-            // Check for special words or Doxygen keywords in comments
-            else if (sc.state == SCE_A68K_COMMENT)
-            {
-                if (sc.ch == '\\') {
-                    sc.SetState(SCE_A68K_COMMENT_DOXYGEN);
-                }
-                else if ((sc.ch < 0x80) && isalpha(sc.ch)) {
-                    sc.SetState(SCE_A68K_COMMENT_WORD);
+            // Strings: include terminal ' or " in the current string by skipping it 
+            if ((sc.state == SCE_A68K_STRING1) || (sc.state == SCE_A68K_STRING2)) { 
+                sc.Forward(); 
                 }
-                continue;
+ 
+ 
+            // If a macro declaration was terminated with ':', it was a label 
+            else if ((sc.state == SCE_A68K_MACRO_DECLARATION) && (sc.chPrev == ':')) { 
+                sc.ChangeState(SCE_A68K_LABEL); 
             }
 
-            // Check for special words in comment
-            else if ((sc.state == SCE_A68K_COMMENT_WORD) && (sc.ch < 0x80) && !isalpha(sc.ch))
-            {
+ 
+            // If it wasn't a Doxygen keyword, change it to normal comment 
+            else if (sc.state == SCE_A68K_COMMENT_DOXYGEN) { 
                 sc.GetCurrent(Buffer, sizeof(Buffer));
-                if (commentSpecial.InList(Buffer)) {
-                    sc.ChangeState(SCE_A68K_COMMENT_SPECIAL);
-                }
-                else {
+                if (!doxygenKeyword.InList(Buffer)) { 
                     sc.ChangeState(SCE_A68K_COMMENT);
                 }
                 sc.SetState(SCE_A68K_COMMENT);
                 continue;
             }
 
-            // Check for Doxygen keywords
-            else if ((sc.state == SCE_A68K_COMMENT_DOXYGEN) && (sc.ch < 0x80) && !IsDoxygenChar(sc.ch))
-            {
-                sc.GetCurrentLowered(Buffer, sizeof(Buffer));                           // Buffer the string 
of the current context
-                if (!doxygenKeyword.InList(Buffer)) {
+ 
+            // If it wasn't an Alert, change it to normal comment 
+            else if (sc.state == SCE_A68K_COMMENT_SPECIAL) { 
+                sc.GetCurrent(Buffer, sizeof(Buffer)); 
+                if (!alert.InList(Buffer)) { 
                     sc.ChangeState(SCE_A68K_COMMENT);
                 }
+                // Reset style to normal comment, or to Doxygen keyword if it begins with '\'  
+                if (sc.ch == '\\') { 
+                    sc.SetState(SCE_A68K_COMMENT_DOXYGEN); 
+                } 
+                else { 
                 sc.SetState(SCE_A68K_COMMENT);
+                } 
                 continue;
             }
 
-            // Check if we are in the case of a label which terminates without ':'
-            // It should be a macro declaration, not a label
-            else if ((sc.state == SCE_A68K_LABEL) && (sc.ch < 0x80) && ((sc.ch == ' ') || (sc.ch == '\t')))
-            {
-                sc.ChangeState(SCE_A68K_MACRO_DECLARATION);
+ 
+            // If we are in a comment, it's a Doxygen keyword or an Alert 
+            else if (sc.state == SCE_A68K_COMMENT) { 
+                if (sc.ch == '\\') { 
+                    sc.SetState(SCE_A68K_COMMENT_DOXYGEN); 
+                } 
+                else { 
+                    sc.SetState(SCE_A68K_COMMENT_SPECIAL); 
+                } 
+                continue; 
             }
 
+ 
             // Check if we are at the end of an identifier
             // In this case, colourise it if was a keyword.
-            else if ((sc.state == SCE_A68K_IDENTIFIER) && !IsIdentifierChar(sc.ch))
-            {
+            else if ((sc.state == SCE_A68K_IDENTIFIER) && !IsIdentifierChar(sc.ch)) { 
                 sc.GetCurrentLowered(Buffer, sizeof(Buffer));                           // Buffer the string 
of the current context
                 if (cpuInstruction.InList(Buffer)) {                                    // And check if it 
belongs to a keyword list
                     sc.ChangeState(SCE_A68K_CPUINSTRUCTION);
@@ -256,14 +269,30 @@ static void ColouriseA68kDoc (unsigned int startPos, int length, int initStyle,
         *
         ************************************************************/
 
+        // Something which begins at the beginning of a line, and with  
+        // - '\' + an identifier start char, or 
+        // - '\\@' + an identifier start char 
+        // is a local label (second case is used for macro local labels). We set it already as a label, it 
can't be a macro/equ declaration 
+        if (sc.atLineStart && (sc.ch < 0x80) && IsIdentifierStart(sc.chNext) && (sc.ch == '\\')) { 
+            sc.SetState(SCE_A68K_LABEL); 
+        } 
+ 
+        if (sc.atLineStart && (sc.ch < 0x80) && (sc.ch == '\\') && (sc.chNext == '\\')) { 
+            sc.Forward(2); 
+            if ((sc.ch == '@') && IsIdentifierStart(sc.chNext)) { 
+                sc.ChangeState(SCE_A68K_LABEL); 
+                sc.SetState(SCE_A68K_LABEL); 
+            } 
+        } 
+         
         // Label and macro identifiers start at the beginning of a line
-        // We set both as a label, but if it wasn't one (no ':' at the end),
-        // it will be changed as a macro identifier.
+        // We set both as a macro id, but if it wasn't one (':' at the end), 
+        // it will be changed as a label. 
         if (sc.atLineStart && (sc.ch < 0x80) && IsIdentifierStart(sc.ch)) {
-            sc.SetState(SCE_A68K_LABEL);
+            sc.SetState(SCE_A68K_MACRO_DECLARATION); 
         }
-        else if ((sc.ch < 0x80) && (sc.ch == ';')) {                            // Comment
-            sc.SetState(SCE_A68K_COMMENT);
+        else if ((sc.ch < 0x80) && (sc.ch == ';')) {                            // Default: alert in a 
comment. If it doesn't match 
+            sc.SetState(SCE_A68K_COMMENT);                                      // with an alert, it will be 
toggle to a normal comment 
         }
         else if ((sc.ch < 0x80) && isdigit(sc.ch)) {                            // Decimal numbers haven't 
prefix
             sc.SetState(SCE_A68K_NUMBER_DEC);
@@ -280,7 +309,7 @@ static void ColouriseA68kDoc (unsigned int startPos, int length, int initStyle,
         else if ((sc.ch < 0x80) && (sc.ch == '\"')) {                           // String (double-quoted)
             sc.SetState(SCE_A68K_STRING2);
         }
-        else if ((sc.ch < 0x80) && (sc.ch == '\\') && (isdigit(sc.chNext))) {   // Replacement symbols in 
macro
+        else if ((sc.ch < 0x80) && (sc.ch == '\\') && (isdigit(sc.chNext))) {   // Replacement symbols in 
macro are prefixed with '\' 
             sc.SetState(SCE_A68K_MACRO_ARG);
         }
         else if ((sc.ch < 0x80) && IsIdentifierStart(sc.ch)) {                  // An identifier: constant, 
label, etc...
diff --git a/plugins/scintilla/scintilla/lexers/LexAda.cxx b/plugins/scintilla/scintilla/lexers/LexAda.cxx
index 49eb2c6..b11c247 100644
--- a/plugins/scintilla/scintilla/lexers/LexAda.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexAda.cxx
@@ -65,8 +65,6 @@ static void ColouriseWhiteSpace(StyleContext& sc, bool& apostropheStartsAttribut
 static void ColouriseWord(StyleContext& sc, WordList& keywords, bool& apostropheStartsAttribute);
 
 static inline bool IsDelimiterCharacter(int ch);
-static inline bool IsNumberStartCharacter(int ch);
-static inline bool IsNumberCharacter(int ch);
 static inline bool IsSeparatorOrDelimiterCharacter(int ch);
 static bool IsValidIdentifier(const std::string& identifier);
 static bool IsValidNumber(const std::string& number);
@@ -310,19 +308,6 @@ static inline bool IsDelimiterCharacter(int ch) {
        }
 }
 
-static inline bool IsNumberCharacter(int ch) {
-       return IsNumberStartCharacter(ch) ||
-              ch == '_' ||
-              ch == '.' ||
-              ch == '#' ||
-              (ch >= 'a' && ch <= 'f') ||
-              (ch >= 'A' && ch <= 'F');
-}
-
-static inline bool IsNumberStartCharacter(int ch) {
-       return IsADigit(ch);
-}
-
 static inline bool IsSeparatorOrDelimiterCharacter(int ch) {
        return IsASpace(ch) || IsDelimiterCharacter(ch);
 }
diff --git a/plugins/scintilla/scintilla/lexers/LexAsn1.cxx b/plugins/scintilla/scintilla/lexers/LexAsn1.cxx
index 3545b3f..120b895 100644
--- a/plugins/scintilla/scintilla/lexers/LexAsn1.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexAsn1.cxx
@@ -185,4 +185,4 @@ static const char * const asn1WordLists[] = {
        0, };
 
 
-LexerModule lmAns1(SCLEX_ASN1, ColouriseAsn1Doc, "asn1", FoldAsn1Doc, asn1WordLists);
+LexerModule lmAsn1(SCLEX_ASN1, ColouriseAsn1Doc, "asn1", FoldAsn1Doc, asn1WordLists);
diff --git a/plugins/scintilla/scintilla/lexers/LexCPP.cxx b/plugins/scintilla/scintilla/lexers/LexCPP.cxx
index 116ea72..b3c9346 100644
--- a/plugins/scintilla/scintilla/lexers/LexCPP.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexCPP.cxx
@@ -66,9 +66,8 @@ static bool followsReturnKeyword(StyleContext &sc, LexAccessor &styler) {
        int pos = (int) sc.currentPos;
        int currentLine = styler.GetLine(pos);
        int lineStartPos = styler.LineStart(currentLine);
-       char ch;
        while (--pos > lineStartPos) {
-               ch = styler.SafeGetCharAt(pos);
+               char ch = styler.SafeGetCharAt(pos);
                if (ch != ' ' && ch != '\t') {
                        break;
                }
@@ -154,7 +153,7 @@ public:
        bool IsInactive() const {
                return state != 0;
        }
-       bool CurrentIfTaken() {
+       bool CurrentIfTaken() const {
                return (ifTaken & maskLevel()) != 0;
        }
        void StartSection(bool on) {
@@ -189,7 +188,7 @@ public:
 class PPStates {
        std::vector<LinePPState> vlls;
 public:
-       LinePPState ForLine(int line) {
+       LinePPState ForLine(int line) const {
                if ((line > 0) && (vlls.size() > static_cast<size_t>(line))) {
                        return vlls[line];
                } else {
@@ -456,9 +455,9 @@ int SCI_METHOD LexerCPP::WordListSet(int n, const char *wl) {
                        if (n == 4) {
                                // Rebuild preprocessorDefinitions
                                preprocessorDefinitionsStart.clear();
-                               for (int nDefinition = 0; nDefinition < ppDefinitions.len; nDefinition++) {
-                                       char *cpDefinition = ppDefinitions.words[nDefinition];
-                                       char *cpEquals = strchr(cpDefinition, '=');
+                               for (int nDefinition = 0; nDefinition < ppDefinitions.Length(); 
nDefinition++) {
+                                       const char *cpDefinition = ppDefinitions.WordAt(nDefinition);
+                                       const char *cpEquals = strchr(cpDefinition, '=');
                                        if (cpEquals) {
                                                std::string name(cpDefinition, cpEquals - cpDefinition);
                                                std::string val(cpEquals+1);
@@ -673,7 +672,7 @@ void SCI_METHOD LexerCPP::Lex(unsigned int startPos, int length, int initStyle,
                                        sc.SetState(SCE_C_DEFAULT|activitySet);
                                }
                                break;
-                       case SCE_C_PREPROCESSOR:        
+                       case SCE_C_PREPROCESSOR:
                                if (options.stylingWithinPreprocessor) {
                                        if (IsASpace(sc.ch)) {
                                                sc.SetState(SCE_C_DEFAULT|activitySet);
@@ -684,7 +683,11 @@ void SCI_METHOD LexerCPP::Lex(unsigned int startPos, int length, int initStyle,
                                        if ((isIncludePreprocessor && sc.Match('<')) || sc.Match('\"')) {
                                                isStringInPreprocessor = true;
                                        } else if (sc.Match('/', '*')) {
-                                               sc.SetState(SCE_C_PREPROCESSORCOMMENT|activitySet);
+                                               if (sc.Match("/**") || sc.Match("/*!")) {
+                                                       sc.SetState(SCE_C_PREPROCESSORCOMMENTDOC|activitySet);
+                                               } else {
+                                                       sc.SetState(SCE_C_PREPROCESSORCOMMENT|activitySet);
+                                               }
                                                sc.Forward();   // Eat the *
                                        } else if (sc.Match('/', '/')) {
                                                sc.SetState(SCE_C_DEFAULT|activitySet);
@@ -692,6 +695,7 @@ void SCI_METHOD LexerCPP::Lex(unsigned int startPos, int length, int initStyle,
                                }
                                break;
                        case SCE_C_PREPROCESSORCOMMENT:
+                       case SCE_C_PREPROCESSORCOMMENTDOC:
                                if (sc.Match('*', '/')) {
                                        sc.Forward();
                                        sc.ForwardSetState(SCE_C_PREPROCESSOR|activitySet);
diff --git a/plugins/scintilla/scintilla/lexers/LexCoffeeScript.cxx 
b/plugins/scintilla/scintilla/lexers/LexCoffeeScript.cxx
index 96d5d2d..d6e0ea2 100644
--- a/plugins/scintilla/scintilla/lexers/LexCoffeeScript.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexCoffeeScript.cxx
@@ -137,7 +137,7 @@ static void ColouriseCoffeeScriptDoc(unsigned int startPos, int length, int init
 
        // look back to set chPrevNonWhite properly for better regex colouring
        int endPos = startPos + length;
-       if (startPos > 0) {
+        if (startPos > 0 && IsSpaceEquiv(initStyle)) {
                unsigned int back = startPos;
                styler.Flush();
                while (back > 0 && IsSpaceEquiv(styler.StyleAt(--back)))
@@ -147,6 +147,9 @@ static void ColouriseCoffeeScriptDoc(unsigned int startPos, int length, int init
                }
                if (startPos != back) {
                        initStyle = styler.StyleAt(back);
+                       if (IsSpaceEquiv(initStyle)) {
+                               initStyle = SCE_C_DEFAULT;
+                       }
                }
                startPos = back;
        }
@@ -321,7 +324,6 @@ static void ColouriseCoffeeScriptDoc(unsigned int startPos, int length, int init
                                break;
                        case SCE_COFFEESCRIPT_COMMENTBLOCK:
                                if (sc.Match("###")) {
-                                       sc.ChangeState(SCE_C_COMMENT);
                                        sc.Forward();
                                        sc.Forward();
                                        sc.ForwardSetState(SCE_C_DEFAULT);
@@ -333,10 +335,8 @@ static void ColouriseCoffeeScriptDoc(unsigned int startPos, int length, int init
                                if (sc.Match("///")) {
                                        sc.Forward();
                                        sc.Forward();
-                                       sc.ChangeState(SCE_C_REGEX);
                                        sc.ForwardSetState(SCE_C_DEFAULT);
                                } else if (sc.Match('#')) {
-                                       sc.ChangeState(SCE_C_REGEX);
                                        sc.SetState(SCE_COFFEESCRIPT_VERBOSE_REGEX_COMMENT);
                                } else if (sc.ch == '\\') {
                                        sc.Forward();
@@ -344,7 +344,6 @@ static void ColouriseCoffeeScriptDoc(unsigned int startPos, int length, int init
                                break;
                        case SCE_COFFEESCRIPT_VERBOSE_REGEX_COMMENT:
                                if (sc.atLineStart) {
-                                       sc.ChangeState(SCE_C_COMMENT);
                                        sc.SetState(SCE_COFFEESCRIPT_VERBOSE_REGEX);
                                }
                                break;
@@ -378,6 +377,8 @@ static void ColouriseCoffeeScriptDoc(unsigned int startPos, int length, int init
                                sc.Forward();   // Eat the * so it isn't used for the end of the comment
                        } else if (sc.Match("///")) {
                                sc.SetState(SCE_COFFEESCRIPT_VERBOSE_REGEX);
+                               sc.Forward();
+                               sc.Forward();
                        } else if (sc.ch == '/'
                                   && (setOKBeforeRE.Contains(chPrevNonWhite)
                                       || followsReturnKeyword(sc, styler))
@@ -392,11 +393,14 @@ static void ColouriseCoffeeScriptDoc(unsigned int startPos, int length, int init
                        } else if (sc.ch == '\'') {
                                sc.SetState(SCE_C_CHARACTER);
                        } else if (sc.ch == '#') {
-                if (sc.Match("###")) {
-                    sc.SetState(SCE_COFFEESCRIPT_COMMENTBLOCK);
-                } else {
-                    sc.SetState(SCE_C_COMMENTLINE);
-                }
+                               if (sc.Match("###")) {
+                                       sc.SetState(SCE_COFFEESCRIPT_COMMENTBLOCK);
+                                       sc.Forward();
+                                       sc.Forward();
+                                       
+                               } else {
+                                       sc.SetState(SCE_C_COMMENTLINE);
+                               }
                        } else if (isoperator(static_cast<char>(sc.ch))) {
                                sc.SetState(SCE_C_OPERATOR);
                        }
@@ -408,18 +412,6 @@ static void ColouriseCoffeeScriptDoc(unsigned int startPos, int length, int init
                }
                continuationLine = false;
        }
-    // Change temporary coffeescript states into standard C ones.
-    switch (sc.state) {
-        case SCE_COFFEESCRIPT_COMMENTBLOCK:
-            sc.ChangeState(SCE_C_COMMENT);
-            break;
-        case SCE_COFFEESCRIPT_VERBOSE_REGEX:
-            sc.ChangeState(SCE_C_REGEX);
-            break;
-        case SCE_COFFEESCRIPT_VERBOSE_REGEX_COMMENT:
-            sc.ChangeState(SCE_C_COMMENTLINE);
-            break;
-    }
        sc.Complete();
 }
 
diff --git a/plugins/scintilla/scintilla/lexers/LexECL.cxx b/plugins/scintilla/scintilla/lexers/LexECL.cxx
index cf15a62..6a08d58 100644
--- a/plugins/scintilla/scintilla/lexers/LexECL.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexECL.cxx
@@ -47,10 +47,19 @@ using namespace Scintilla;
 #endif
 
 static bool IsSpaceEquiv(int state) {
-       return (state <= SCE_ECL_COMMENTDOC) ||
-               // including SCE_ECL_DEFAULT, SCE_ECL_COMMENT, SCE_ECL_COMMENTLINE
-               (state == SCE_ECL_COMMENTLINEDOC) || (state == SCE_ECL_COMMENTDOCKEYWORD) ||
-               (state == SCE_ECL_COMMENTDOCKEYWORDERROR);
+       switch (state) {
+       case SCE_ECL_DEFAULT:
+       case SCE_ECL_COMMENT:
+       case SCE_ECL_COMMENTLINE:
+       case SCE_ECL_COMMENTLINEDOC:
+       case SCE_ECL_COMMENTDOCKEYWORD:
+       case SCE_ECL_COMMENTDOCKEYWORDERROR:
+       case SCE_ECL_COMMENTDOC:
+               return true;
+
+       default:
+               return false;
+       }
 }
 
 static void ColouriseEclDoc(unsigned int startPos, int length, int initStyle, WordList *keywordlists[],
diff --git a/plugins/scintilla/scintilla/lexers/LexHaskell.cxx 
b/plugins/scintilla/scintilla/lexers/LexHaskell.cxx
index 37d85d0..e10cb8c 100644
--- a/plugins/scintilla/scintilla/lexers/LexHaskell.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexHaskell.cxx
@@ -4,19 +4,20 @@
  *    A haskell lexer for the scintilla code control.
  *    Some stuff "lended" from LexPython.cxx and LexCPP.cxx.
  *    External lexer stuff inspired from the caml external lexer.
+ *    Folder copied from Python's.
  *
  *    Written by Tobias Engvall - tumm at dtek dot chalmers dot se
  *
  *    Several bug fixes by Krasimir Angelov - kr.angelov at gmail.com
  *
- *    TODO:
- *    * Implement a folder :)
- *    * Nice Character-lexing (stuff inside '\''), LexPython has
- *      this.
+ *    Improved by kudah <kudahkukarek gmail com>
  *
+ *    TODO:
+ *    * A proper lexical folder to fold group declarations, comments, pragmas,
+ *      #ifdefs, explicit layout, lists, tuples, quasi-quotes, splces, etc, etc,
+ *      etc.
  *
  *****************************************************************/
-
 #include <stdlib.h>
 #include <string.h>
 #include <stdio.h>
@@ -24,6 +25,9 @@
 #include <assert.h>
 #include <ctype.h>
 
+#include <string>
+#include <map>
+
 #include "ILexer.h"
 #include "Scintilla.h"
 #include "SciLexer.h"
@@ -35,334 +39,1073 @@
 #include "StyleContext.h"
 #include "CharacterSet.h"
 #include "LexerModule.h"
+#include "OptionSet.h"
+#include "CharacterCategory.h"
 
 #ifdef SCI_NAMESPACE
 using namespace Scintilla;
 #endif
 
-#ifdef BUILD_AS_EXTERNAL_LEXER
+// See https://github.com/ghc/ghc/blob/master/compiler/parser/Lexer.x#L1682
+// Note, letter modifiers are prohibited.
 
-#include "ExternalLexer.h"
-#include "WindowAccessor.h"
+static int u_iswupper (int ch) {
+   CharacterCategory c = CategoriseCharacter(ch);
+   return c == ccLu || c == ccLt;
+}
 
-#define BUILD_EXTERNAL_LEXER 0
+static int u_iswalpha (int ch) {
+   CharacterCategory c = CategoriseCharacter(ch);
+   return c == ccLl || c == ccLu || c == ccLt || c == ccLo;
+}
 
-#endif
+static int u_iswalnum (int ch) {
+   CharacterCategory c = CategoriseCharacter(ch);
+   return c == ccLl || c == ccLu || c == ccLt || c == ccLo
+       || c == ccNd || c == ccNo;
+}
+
+static int u_IsHaskellSymbol(int ch) {
+   CharacterCategory c = CategoriseCharacter(ch);
+   return c == ccPc || c == ccPd || c == ccPo
+       || c == ccSm || c == ccSc || c == ccSk || c == ccSo;
+}
 
-#define HA_MODE_DEFAULT     0
-#define HA_MODE_IMPORT1     1
-#define HA_MODE_IMPORT2     2
-#define HA_MODE_IMPORT3     3
-#define HA_MODE_MODULE      4
-#define HA_MODE_FFI         5
-#define HA_MODE_TYPE        6
+static inline bool IsHaskellLetter(const int ch) {
+   if (IsASCII(ch)) {
+      return (ch >= 'a' && ch <= 'z')
+          || (ch >= 'A' && ch <= 'Z');
+   } else {
+      return u_iswalpha(ch) != 0;
+   }
+}
 
-static inline bool IsNewline(const int ch) {
-   return (ch == '\n' || ch == '\r');
+static inline bool IsHaskellAlphaNumeric(const int ch) {
+   if (IsASCII(ch)) {
+      return IsAlphaNumeric(ch);
+   } else {
+      return u_iswalnum(ch) != 0;
+   }
 }
 
-static inline bool IsWhitespace(const int ch) {
-   return (  ch == ' '
-          || ch == '\t'
-          || IsNewline(ch) );
+static inline bool IsHaskellUpperCase(const int ch) {
+   if (IsASCII(ch)) {
+      return ch >= 'A' && ch <= 'Z';
+   } else {
+      return u_iswupper(ch) != 0;
+   }
 }
 
-static inline bool IsAWordStart(const int ch) {
-   return (ch < 0x80) && (isalnum(ch) || ch == '_');
+static inline bool IsAnHaskellOperatorChar(const int ch) {
+   if (IsASCII(ch)) {
+      return
+         (  ch == '!' || ch == '#' || ch == '$' || ch == '%'
+         || ch == '&' || ch == '*' || ch == '+' || ch == '-'
+         || ch == '.' || ch == '/' || ch == ':' || ch == '<'
+         || ch == '=' || ch == '>' || ch == '?' || ch == '@'
+         || ch == '^' || ch == '|' || ch == '~' || ch == '\\');
+   } else {
+      return u_IsHaskellSymbol(ch) != 0;
+   }
 }
 
-static inline bool IsAWordChar(const int ch) {
-   return (ch < 0x80) && (isalnum(ch) || ch == '.' || ch == '_' || ch == '\'');
+static inline bool IsAHaskellWordStart(const int ch) {
+   return IsHaskellLetter(ch) || ch == '_';
 }
 
-static void ColorizeHaskellDoc(unsigned int startPos, int length, int initStyle,
-                               WordList *keywordlists[], Accessor &styler) {
+static inline bool IsAHaskellWordChar(const int ch) {
+   return (  IsHaskellAlphaNumeric(ch)
+          || ch == '_'
+          || ch == '\'');
+}
 
-   WordList &keywords = *keywordlists[0];
-   WordList &ffi      = *keywordlists[1];
+static inline bool IsCommentBlockStyle(int style) {
+   return (style >= SCE_HA_COMMENTBLOCK && style <= SCE_HA_COMMENTBLOCK3);
+}
 
-   StyleContext sc(startPos, length, initStyle, styler);
+static inline bool IsCommentStyle(int style) {
+   return (style >= SCE_HA_COMMENTLINE && style <= SCE_HA_COMMENTBLOCK3)
+       || ( style == SCE_HA_LITERATE_COMMENT
+         || style == SCE_HA_LITERATE_CODEDELIM);
+}
+
+// styles which do not belong to Haskell, but to external tools
+static inline bool IsExternalStyle(int style) {
+   return ( style == SCE_HA_PREPROCESSOR
+         || style == SCE_HA_LITERATE_COMMENT
+         || style == SCE_HA_LITERATE_CODEDELIM);
+}
+
+static inline int CommentBlockStyleFromNestLevel(const unsigned int nestLevel) {
+   return SCE_HA_COMMENTBLOCK + (nestLevel % 3);
+}
+
+// Mangled version of lexlib/Accessor.cxx IndentAmount.
+// Modified to treat comment blocks as whitespace
+// plus special case for commentline/preprocessor.
+static int HaskellIndentAmount(Accessor &styler, const int line) {
+
+   // Determines the indentation level of the current line
+   // Comment blocks are treated as whitespace
+
+   int pos = styler.LineStart(line);
+   int eol_pos = styler.LineStart(line + 1) - 1;
+
+   char ch = styler[pos];
+   int style = styler.StyleAt(pos);
+
+   int indent = 0;
+   bool inPrevPrefix = line > 0;
+
+   int posPrev = inPrevPrefix ? styler.LineStart(line-1) : 0;
+
+   while ((  ch == ' ' || ch == '\t'
+          || IsCommentBlockStyle(style)
+          || style == SCE_HA_LITERATE_CODEDELIM)
+         && (pos < eol_pos)) {
+      if (inPrevPrefix) {
+         char chPrev = styler[posPrev++];
+         if (chPrev != ' ' && chPrev != '\t') {
+            inPrevPrefix = false;
+         }
+      }
+      if (ch == '\t') {
+         indent = (indent / 8 + 1) * 8;
+      } else { // Space or comment block
+         indent++;
+      }
+      pos++;
+      ch = styler[pos];
+      style = styler.StyleAt(pos);
+   }
+
+   indent += SC_FOLDLEVELBASE;
+   // if completely empty line or the start of a comment or preprocessor...
+   if (  styler.LineStart(line) == styler.Length()
+      || ch == ' '
+      || ch == '\t'
+      || ch == '\n'
+      || ch == '\r'
+      || IsCommentStyle(style)
+      || style == SCE_HA_PREPROCESSOR)
+      return indent | SC_FOLDLEVELWHITEFLAG;
+   else
+      return indent;
+}
+
+struct OptionsHaskell {
+   bool magicHash;
+   bool allowQuotes;
+   bool implicitParams;
+   bool highlightSafe;
+   bool cpp;
+   bool stylingWithinPreprocessor;
+   bool fold;
+   bool foldComment;
+   bool foldCompact;
+   bool foldImports;
+   OptionsHaskell() {
+      magicHash = true;       // Widespread use, enabled by default.
+      allowQuotes = true;     // Widespread use, enabled by default.
+      implicitParams = false; // Fell out of favor, seldom used, disabled.
+      highlightSafe = true;   // Moderately used, doesn't hurt to enable.
+      cpp = true;             // Widespread use, enabled by default;
+      stylingWithinPreprocessor = false;
+      fold = false;
+      foldComment = false;
+      foldCompact = false;
+      foldImports = false;
+   }
+};
+
+static const char * const haskellWordListDesc[] = {
+   "Keywords",
+   "FFI",
+   "Reserved operators",
+   0
+};
+
+struct OptionSetHaskell : public OptionSet<OptionsHaskell> {
+   OptionSetHaskell() {
+      DefineProperty("lexer.haskell.allow.hash", &OptionsHaskell::magicHash,
+         "Set to 0 to disallow the '#' character at the end of identifiers and "
+         "literals with the haskell lexer "
+         "(GHC -XMagicHash extension)");
+
+      DefineProperty("lexer.haskell.allow.quotes", &OptionsHaskell::allowQuotes,
+         "Set to 0 to disable highlighting of Template Haskell name quotations "
+         "and promoted constructors "
+         "(GHC -XTemplateHaskell and -XDataKinds extensions)");
+
+      DefineProperty("lexer.haskell.allow.questionmark", &OptionsHaskell::implicitParams,
+         "Set to 1 to allow the '?' character at the start of identifiers "
+         "with the haskell lexer "
+         "(GHC & Hugs -XImplicitParams extension)");
+
+      DefineProperty("lexer.haskell.import.safe", &OptionsHaskell::highlightSafe,
+         "Set to 0 to disallow \"safe\" keyword in imports "
+         "(GHC -XSafe, -XTrustworthy, -XUnsafe extensions)");
+
+      DefineProperty("lexer.haskell.cpp", &OptionsHaskell::cpp,
+         "Set to 0 to disable C-preprocessor highlighting "
+         "(-XCPP extension)");
+
+      DefineProperty("styling.within.preprocessor", &OptionsHaskell::stylingWithinPreprocessor,
+         "For Haskell code, determines whether all preprocessor code is styled in the "
+         "preprocessor style (0, the default) or only from the initial # to the end "
+         "of the command word(1)."
+         );
+
+      DefineProperty("fold", &OptionsHaskell::fold);
+
+      DefineProperty("fold.comment", &OptionsHaskell::foldComment);
+
+      DefineProperty("fold.compact", &OptionsHaskell::foldCompact);
+
+      DefineProperty("fold.haskell.imports", &OptionsHaskell::foldImports,
+         "Set to 1 to enable folding of import declarations");
+
+      DefineWordListSets(haskellWordListDesc);
+   }
+};
+
+class LexerHaskell : public ILexer {
+   bool literate;
+   int firstImportLine;
+   int firstImportIndent;
+   WordList keywords;
+   WordList ffi;
+   WordList reserved_operators;
+   OptionsHaskell options;
+   OptionSetHaskell osHaskell;
+
+   enum HashCount {
+       oneHash
+      ,twoHashes
+      ,unlimitedHashes
+   };
+
+   enum KeywordMode {
+       HA_MODE_DEFAULT = 0
+      ,HA_MODE_IMPORT1 = 1 // after "import", before "qualified" or "safe" or package name or module name.
+      ,HA_MODE_IMPORT2 = 2 // after module name, before "as" or "hiding".
+      ,HA_MODE_IMPORT3 = 3 // after "as", before "hiding"
+      ,HA_MODE_MODULE  = 4 // after "module", before module name.
+      ,HA_MODE_FFI     = 5 // after "foreign", before FFI keywords
+      ,HA_MODE_TYPE    = 6 // after "type" or "data", before "family"
+   };
+
+   enum LiterateMode {
+       LITERATE_BIRD  = 0 // if '>' is the first character on the line,
+                          //   color '>' as a codedelim and the rest of
+                          //   the line as code.
+                          // else if "\begin{code}" is the only word on the
+                          //    line except whitespace, switch to LITERATE_BLOCK
+                          // otherwise color the line as a literate comment.
+      ,LITERATE_BLOCK = 1 // if the string "\end{code}" is encountered at column
+                          //   0 ignoring all later characters, color the line
+                          //   as a codedelim and switch to LITERATE_BIRD
+                          // otherwise color the line as code.
+   };
+
+   struct HaskellLineInfo {
+      unsigned int nestLevel; // 22 bits ought to be enough for anybody
+      unsigned int nonexternalStyle; // 5 bits, widen if number of styles goes
+                                     // beyond 31.
+      bool pragma;
+      LiterateMode lmode;
+      KeywordMode mode;
+
+      HaskellLineInfo(int state) :
+         nestLevel (state >> 10)
+       , nonexternalStyle ((state >> 5) & 0x1F)
+       , pragma ((state >> 4) & 0x1)
+       , lmode (static_cast<LiterateMode>((state >> 3) & 0x1))
+       , mode (static_cast<KeywordMode>(state & 0x7))
+         {}
+
+      int ToLineState() {
+         return
+              (nestLevel << 10)
+            | (nonexternalStyle << 5)
+            | (pragma << 4)
+            | (lmode << 3)
+            | mode;
+      }
+   };
+
+   inline void skipMagicHash(StyleContext &sc, const HashCount hashes) const {
+      if (options.magicHash && sc.ch == '#') {
+         sc.Forward();
+         if (hashes == twoHashes && sc.ch == '#') {
+            sc.Forward();
+         } else if (hashes == unlimitedHashes) {
+            while (sc.ch == '#') {
+               sc.Forward();
+            }
+         }
+      }
+   }
+
+   bool LineContainsImport(const int line, Accessor &styler) const {
+      if (options.foldImports) {
+         int currentPos = styler.LineStart(line);
+         int style = styler.StyleAt(currentPos);
+
+         int eol_pos = styler.LineStart(line + 1) - 1;
+
+         while (currentPos < eol_pos) {
+            int ch = styler[currentPos];
+            style = styler.StyleAt(currentPos);
+
+            if (ch == ' ' || ch == '\t'
+             || IsCommentBlockStyle(style)
+             || style == SCE_HA_LITERATE_CODEDELIM) {
+               currentPos++;
+            } else {
+               break;
+            }
+         }
+
+         return (style == SCE_HA_KEYWORD
+              && styler.Match(currentPos, "import"));
+      } else {
+         return false;
+      }
+   }
+
+   inline int IndentAmountWithOffset(Accessor &styler, const int line) const {
+      const int indent = HaskellIndentAmount(styler, line);
+      const int indentLevel = indent & SC_FOLDLEVELNUMBERMASK;
+      return indentLevel <= ((firstImportIndent - 1) + SC_FOLDLEVELBASE)
+               ? indent
+               : (indentLevel + firstImportIndent) | (indent & ~SC_FOLDLEVELNUMBERMASK);
+   }
+
+   inline int IndentLevelRemoveIndentOffset(const int indentLevel) const {
+      return indentLevel <= ((firstImportIndent - 1) + SC_FOLDLEVELBASE)
+            ? indentLevel
+            : indentLevel - firstImportIndent;
+   }
+
+public:
+   LexerHaskell(bool literate_)
+      : literate(literate_)
+      , firstImportLine(-1)
+      , firstImportIndent(0)
+      {}
+   virtual ~LexerHaskell() {}
+
+   void SCI_METHOD Release() {
+      delete this;
+   }
+
+   int SCI_METHOD Version() const {
+      return lvOriginal;
+   }
+
+   const char * SCI_METHOD PropertyNames() {
+      return osHaskell.PropertyNames();
+   }
+
+   int SCI_METHOD PropertyType(const char *name) {
+      return osHaskell.PropertyType(name);
+   }
+
+   const char * SCI_METHOD DescribeProperty(const char *name) {
+      return osHaskell.DescribeProperty(name);
+   }
+
+   int SCI_METHOD PropertySet(const char *key, const char *val);
+
+   const char * SCI_METHOD DescribeWordListSets() {
+      return osHaskell.DescribeWordListSets();
+   }
+
+   int SCI_METHOD WordListSet(int n, const char *wl);
+
+   void SCI_METHOD Lex(unsigned int startPos, int length, int initStyle, IDocument *pAccess);
+
+   void SCI_METHOD Fold(unsigned int startPos, int length, int initStyle, IDocument *pAccess);
+
+   void * SCI_METHOD PrivateCall(int, void *) {
+      return 0;
+   }
+
+   static ILexer *LexerFactoryHaskell() {
+      return new LexerHaskell(false);
+   }
+
+   static ILexer *LexerFactoryLiterateHaskell() {
+      return new LexerHaskell(true);
+   }
+};
+
+int SCI_METHOD LexerHaskell::PropertySet(const char *key, const char *val) {
+   if (osHaskell.PropertySet(&options, key, val)) {
+      return 0;
+   }
+   return -1;
+}
+
+int SCI_METHOD LexerHaskell::WordListSet(int n, const char *wl) {
+   WordList *wordListN = 0;
+   switch (n) {
+   case 0:
+      wordListN = &keywords;
+      break;
+   case 1:
+      wordListN = &ffi;
+      break;
+   case 2:
+      wordListN = &reserved_operators;
+      break;
+   }
+   int firstModification = -1;
+   if (wordListN) {
+      WordList wlNew;
+      wlNew.Set(wl);
+      if (*wordListN != wlNew) {
+         wordListN->Set(wl);
+         firstModification = 0;
+      }
+   }
+   return firstModification;
+}
+
+void SCI_METHOD LexerHaskell::Lex(unsigned int startPos, int length, int initStyle
+                                 ,IDocument *pAccess) {
+   LexAccessor styler(pAccess);
 
    int lineCurrent = styler.GetLine(startPos);
-   int state = lineCurrent ? styler.GetLineState(lineCurrent-1)
-                           : HA_MODE_DEFAULT;
-   int mode  = state & 0xF;
-   int xmode = state >> 4;
+
+   HaskellLineInfo hs = HaskellLineInfo(lineCurrent ? styler.GetLineState(lineCurrent-1) : 0);
+
+   // Do not leak onto next line
+   if (initStyle == SCE_HA_STRINGEOL)
+      initStyle = SCE_HA_DEFAULT;
+   else if (initStyle == SCE_HA_LITERATE_CODEDELIM)
+      initStyle = hs.nonexternalStyle;
+
+   StyleContext sc(startPos, length, initStyle, styler);
+
+   int base = 10;
+   bool dot = false;
+
+   bool inDashes = false;
+   bool alreadyInTheMiddleOfOperator = false;
+
+   assert(!(IsCommentBlockStyle(initStyle) && hs.nestLevel == 0));
 
    while (sc.More()) {
       // Check for state end
 
-         // Operator
-      if (sc.state == SCE_HA_OPERATOR) {
-         if (isascii(sc.ch) && isoperator(static_cast<char>(sc.ch))) {
+      if (!IsExternalStyle(sc.state)) {
+         hs.nonexternalStyle = sc.state;
+      }
+
+      // For lexer to work, states should unconditionally forward at least one
+      // character.
+      // If they don't, they should still check if they are at line end and
+      // forward if so.
+      // If a state forwards more than one character, it should check every time
+      // that it is not a line end and cease forwarding otherwise.
+      if (sc.atLineEnd) {
+         // Remember the line state for future incremental lexing
+         styler.SetLineState(lineCurrent, hs.ToLineState());
+         lineCurrent++;
+      }
+
+      // Handle line continuation generically.
+      if (sc.ch == '\\' && (sc.chNext == '\n' || sc.chNext == '\r')
+         && (  sc.state == SCE_HA_STRING
+            || sc.state == SCE_HA_PREPROCESSOR)) {
+         // Remember the line state for future incremental lexing
+         styler.SetLineState(lineCurrent, hs.ToLineState());
+         lineCurrent++;
+
+         sc.Forward();
+         if (sc.ch == '\r' && sc.chNext == '\n') {
+            sc.Forward();
+         }
+         sc.Forward();
+
+         continue;
+      }
+
+      if (sc.atLineStart) {
+
+         if (sc.state == SCE_HA_STRING || sc.state == SCE_HA_CHARACTER) {
+            // Prevent SCE_HA_STRINGEOL from leaking back to previous line
+            sc.SetState(sc.state);
+         }
+
+         if (literate && hs.lmode == LITERATE_BIRD) {
+            if (!IsExternalStyle(sc.state)) {
+               sc.SetState(SCE_HA_LITERATE_COMMENT);
+            }
+         }
+      }
+
+      // External
+         // Literate
+      if (  literate && hs.lmode == LITERATE_BIRD && sc.atLineStart
+         && sc.ch == '>') {
+            sc.SetState(SCE_HA_LITERATE_CODEDELIM);
+            sc.ForwardSetState(hs.nonexternalStyle);
+      }
+      else if (literate && hs.lmode == LITERATE_BIRD && sc.atLineStart
+            && (  sc.ch == ' ' || sc.ch == '\t'
+               || sc.Match("\\begin{code}"))) {
+         sc.SetState(sc.state);
+
+         while ((sc.ch == ' ' || sc.ch == '\t') && sc.More())
             sc.Forward();
+
+         if (sc.Match("\\begin{code}")) {
+            sc.Forward(static_cast<int>(strlen("\\begin{code}")));
+
+            bool correct = true;
+
+            while (!sc.atLineEnd && sc.More()) {
+               if (sc.ch != ' ' && sc.ch != '\t') {
+                  correct = false;
+               }
+               sc.Forward();
+            }
+
+            if (correct) {
+               sc.ChangeState(SCE_HA_LITERATE_CODEDELIM); // color the line end
+               hs.lmode = LITERATE_BLOCK;
+            }
+         }
+      }
+      else if (literate && hs.lmode == LITERATE_BLOCK && sc.atLineStart
+            && sc.Match("\\end{code}")) {
+         sc.SetState(SCE_HA_LITERATE_CODEDELIM);
+
+         sc.Forward(static_cast<int>(strlen("\\end{code}")));
+
+         while (!sc.atLineEnd && sc.More()) {
+            sc.Forward();
+         }
+
+         sc.SetState(SCE_HA_LITERATE_COMMENT);
+         hs.lmode = LITERATE_BIRD;
+      }
+         // Preprocessor
+      else if (sc.atLineStart && sc.ch == '#' && options.cpp
+            && (!options.stylingWithinPreprocessor || sc.state == SCE_HA_DEFAULT)) {
+         sc.SetState(SCE_HA_PREPROCESSOR);
+         sc.Forward();
+      }
+            // Literate
+      else if (sc.state == SCE_HA_LITERATE_COMMENT) {
+         sc.Forward();
+      }
+      else if (sc.state == SCE_HA_LITERATE_CODEDELIM) {
+         sc.ForwardSetState(hs.nonexternalStyle);
+      }
+            // Preprocessor
+      else if (sc.state == SCE_HA_PREPROCESSOR) {
+         if (sc.atLineEnd) {
+            sc.SetState(options.stylingWithinPreprocessor
+                        ? SCE_HA_DEFAULT
+                        : hs.nonexternalStyle);
+            sc.Forward(); // prevent double counting a line
+         } else if (options.stylingWithinPreprocessor && !IsHaskellLetter(sc.ch)) {
+            sc.SetState(SCE_HA_DEFAULT);
          } else {
-            styler.ColourTo(sc.currentPos - 1, sc.state);
-            sc.ChangeState(SCE_HA_DEFAULT);
+            sc.Forward();
          }
       }
+      // Haskell
+         // Operator
+      else if (sc.state == SCE_HA_OPERATOR) {
+         int style = SCE_HA_OPERATOR;
+
+         if ( sc.ch == ':'
+            && !alreadyInTheMiddleOfOperator
+            // except "::"
+            && !( sc.chNext == ':'
+               && !IsAnHaskellOperatorChar(sc.GetRelative(2)))) {
+            style = SCE_HA_CAPITAL;
+         }
+
+         alreadyInTheMiddleOfOperator = false;
+
+         while (IsAnHaskellOperatorChar(sc.ch))
+               sc.Forward();
+
+         char s[100];
+         sc.GetCurrent(s, sizeof(s));
+
+         if (reserved_operators.InList(s))
+            style = SCE_HA_RESERVED_OPERATOR;
+
+         sc.ChangeState(style);
+         sc.SetState(SCE_HA_DEFAULT);
+      }
          // String
       else if (sc.state == SCE_HA_STRING) {
-         if (sc.ch == '\"') {
-                       sc.Forward();
-            styler.ColourTo(sc.currentPos-1, sc.state);
-            sc.ChangeState(SCE_HA_DEFAULT);
+         if (sc.atLineEnd) {
+            sc.ChangeState(SCE_HA_STRINGEOL);
+            sc.ForwardSetState(SCE_HA_DEFAULT);
+         } else if (sc.ch == '\"') {
+            sc.Forward();
+            skipMagicHash(sc, oneHash);
+            sc.SetState(SCE_HA_DEFAULT);
          } else if (sc.ch == '\\') {
             sc.Forward(2);
-         } else if (sc.atLineEnd) {
-                       styler.ColourTo(sc.currentPos-1, sc.state);
-                       sc.ChangeState(SCE_HA_DEFAULT);
-                } else {
-                       sc.Forward();
-                }
+         } else {
+            sc.Forward();
+         }
       }
          // Char
       else if (sc.state == SCE_HA_CHARACTER) {
-         if (sc.ch == '\'') {
-                       sc.Forward();
-            styler.ColourTo(sc.currentPos-1, sc.state);
-            sc.ChangeState(SCE_HA_DEFAULT);
+         if (sc.atLineEnd) {
+            sc.ChangeState(SCE_HA_STRINGEOL);
+            sc.ForwardSetState(SCE_HA_DEFAULT);
+         } else if (sc.ch == '\'') {
+            sc.Forward();
+            skipMagicHash(sc, oneHash);
+            sc.SetState(SCE_HA_DEFAULT);
          } else if (sc.ch == '\\') {
             sc.Forward(2);
-         } else if (sc.atLineEnd) {
-                       styler.ColourTo(sc.currentPos-1, sc.state);
-                       sc.ChangeState(SCE_HA_DEFAULT);
-                } else {
-                       sc.Forward();
-                }
+         } else {
+            sc.Forward();
+         }
       }
          // Number
       else if (sc.state == SCE_HA_NUMBER) {
-         if (IsADigit(sc.ch, xmode)) {
+         if (sc.atLineEnd) {
+            sc.SetState(SCE_HA_DEFAULT);
+            sc.Forward(); // prevent double counting a line
+         } else if (IsADigit(sc.ch, base)) {
             sc.Forward();
-         } else if ((xmode == 10) &&
+         } else if (sc.ch=='.' && dot && IsADigit(sc.chNext, base)) {
+            sc.Forward(2);
+            dot = false;
+         } else if ((base == 10) &&
                     (sc.ch == 'e' || sc.ch == 'E') &&
                     (IsADigit(sc.chNext) || sc.chNext == '+' || sc.chNext == '-')) {
-                       sc.Forward();
-                       if (sc.ch == '+' || sc.ch == '-')
-                               sc.Forward();
+            sc.Forward();
+            if (sc.ch == '+' || sc.ch == '-')
+                sc.Forward();
          } else {
-            styler.ColourTo(sc.currentPos - 1, sc.state);
-            sc.ChangeState(SCE_HA_DEFAULT);
+            skipMagicHash(sc, twoHashes);
+            sc.SetState(SCE_HA_DEFAULT);
          }
       }
-         // Identifier
+         // Keyword or Identifier
       else if (sc.state == SCE_HA_IDENTIFIER) {
-         if (IsAWordChar(sc.ch)) {
-            sc.Forward();
-         } else {
-            char s[100];
-            sc.GetCurrent(s, sizeof(s));
-            int style = sc.state;
-            int new_mode = 0;
-            if (keywords.InList(s)) {
-               style = SCE_HA_KEYWORD;
-            } else if (isupper(s[0])) {
-               if (mode >= HA_MODE_IMPORT1 && mode <= HA_MODE_IMPORT3) {
-                  style    = SCE_HA_MODULE;
-                  new_mode = HA_MODE_IMPORT2;
-               } else if (mode == HA_MODE_MODULE)
-                  style = SCE_HA_MODULE;
-               else
+         int style = IsHaskellUpperCase(sc.ch) ? SCE_HA_CAPITAL : SCE_HA_IDENTIFIER;
+
+         assert(IsAHaskellWordStart(sc.ch));
+
+         sc.Forward();
+
+         while (sc.More()) {
+            if (IsAHaskellWordChar(sc.ch)) {
+               sc.Forward();
+            } else if (sc.ch == '.' && style == SCE_HA_CAPITAL) {
+               if (IsHaskellUpperCase(sc.chNext)) {
+                  sc.Forward();
                   style = SCE_HA_CAPITAL;
-            } else if (mode == HA_MODE_IMPORT1 &&
-                       strcmp(s,"qualified") == 0) {
-                style    = SCE_HA_KEYWORD;
-                new_mode = HA_MODE_IMPORT1;
-            } else if (mode == HA_MODE_IMPORT2) {
-                if (strcmp(s,"as") == 0) {
-                   style    = SCE_HA_KEYWORD;
-                   new_mode = HA_MODE_IMPORT3;
-               } else if (strcmp(s,"hiding") == 0) {
-                   style     = SCE_HA_KEYWORD;
-               }
-            } else if (mode == HA_MODE_FFI) {
-                          if (ffi.InList(s)) {
-                  style = SCE_HA_KEYWORD;
-                  new_mode = HA_MODE_FFI;
+               } else if (IsAHaskellWordStart(sc.chNext)) {
+                  sc.Forward();
+                  style = SCE_HA_IDENTIFIER;
+               } else if (IsAnHaskellOperatorChar(sc.chNext)) {
+                  sc.Forward();
+                  style = sc.ch == ':' ? SCE_HA_CAPITAL : SCE_HA_OPERATOR;
+                  while (IsAnHaskellOperatorChar(sc.ch))
+                     sc.Forward();
+                  break;
+               } else {
+                  break;
                }
+            } else {
+               break;
+            }
+         }
+
+         skipMagicHash(sc, unlimitedHashes);
+
+         char s[100];
+         sc.GetCurrent(s, sizeof(s));
+
+         KeywordMode new_mode = HA_MODE_DEFAULT;
+
+         if (keywords.InList(s)) {
+            style = SCE_HA_KEYWORD;
+         } else if (style == SCE_HA_CAPITAL) {
+            if (hs.mode == HA_MODE_IMPORT1 || hs.mode == HA_MODE_IMPORT3) {
+               style    = SCE_HA_MODULE;
+               new_mode = HA_MODE_IMPORT2;
+            } else if (hs.mode == HA_MODE_MODULE) {
+               style = SCE_HA_MODULE;
             }
-            else if (mode == HA_MODE_TYPE) {
-               if (strcmp(s,"family") == 0)
-                  style    = SCE_HA_KEYWORD;
-                       }
-            styler.ColourTo(sc.currentPos - 1, style);
-            if (strcmp(s,"import") == 0 && mode != HA_MODE_FFI)
-               new_mode = HA_MODE_IMPORT1;
-            else if (strcmp(s,"module") == 0)
-               new_mode = HA_MODE_MODULE;
-            else if (strcmp(s,"foreign") == 0)
+         } else if (hs.mode == HA_MODE_IMPORT1 &&
+                    strcmp(s,"qualified") == 0) {
+             style    = SCE_HA_KEYWORD;
+             new_mode = HA_MODE_IMPORT1;
+         } else if (options.highlightSafe &&
+                    hs.mode == HA_MODE_IMPORT1 &&
+                    strcmp(s,"safe") == 0) {
+             style    = SCE_HA_KEYWORD;
+             new_mode = HA_MODE_IMPORT1;
+         } else if (hs.mode == HA_MODE_IMPORT2) {
+             if (strcmp(s,"as") == 0) {
+                style    = SCE_HA_KEYWORD;
+                new_mode = HA_MODE_IMPORT3;
+            } else if (strcmp(s,"hiding") == 0) {
+                style     = SCE_HA_KEYWORD;
+            }
+         } else if (hs.mode == HA_MODE_TYPE) {
+            if (strcmp(s,"family") == 0)
+               style    = SCE_HA_KEYWORD;
+         }
+
+         if (hs.mode == HA_MODE_FFI) {
+            if (ffi.InList(s)) {
+               style = SCE_HA_KEYWORD;
                new_mode = HA_MODE_FFI;
-            else if (strcmp(s,"type") == 0)
-               new_mode = HA_MODE_TYPE;
-            sc.ChangeState(SCE_HA_DEFAULT);
-            mode = new_mode;
+            }
          }
+
+         sc.ChangeState(style);
+         sc.SetState(SCE_HA_DEFAULT);
+
+         if (strcmp(s,"import") == 0 && hs.mode != HA_MODE_FFI)
+            new_mode = HA_MODE_IMPORT1;
+         else if (strcmp(s,"module") == 0)
+            new_mode = HA_MODE_MODULE;
+         else if (strcmp(s,"foreign") == 0)
+            new_mode = HA_MODE_FFI;
+         else if (strcmp(s,"type") == 0
+               || strcmp(s,"data") == 0)
+            new_mode = HA_MODE_TYPE;
+
+         hs.mode = new_mode;
       }
 
          // Comments
             // Oneliner
       else if (sc.state == SCE_HA_COMMENTLINE) {
          if (sc.atLineEnd) {
-            styler.ColourTo(sc.currentPos - 1, sc.state);
-            sc.ChangeState(SCE_HA_DEFAULT);
+            sc.SetState(hs.pragma ? SCE_HA_PRAGMA : SCE_HA_DEFAULT);
+            sc.Forward(); // prevent double counting a line
+         } else if (inDashes && sc.ch != '-' && !hs.pragma) {
+            inDashes = false;
+            if (IsAnHaskellOperatorChar(sc.ch)) {
+               alreadyInTheMiddleOfOperator = true;
+               sc.ChangeState(SCE_HA_OPERATOR);
+            }
          } else {
             sc.Forward();
          }
       }
             // Nested
-      else if (sc.state == SCE_HA_COMMENTBLOCK) {
-         if (sc.Match("{-")) {
+      else if (IsCommentBlockStyle(sc.state)) {
+         if (sc.Match('{','-')) {
+            sc.SetState(CommentBlockStyleFromNestLevel(hs.nestLevel));
             sc.Forward(2);
-            xmode++;
+            hs.nestLevel++;
+         } else if (sc.Match('-','}')) {
+            sc.Forward(2);
+            assert(hs.nestLevel > 0);
+            if (hs.nestLevel > 0)
+               hs.nestLevel--;
+            sc.SetState(
+               hs.nestLevel == 0
+                  ? (hs.pragma ? SCE_HA_PRAGMA : SCE_HA_DEFAULT)
+                  : CommentBlockStyleFromNestLevel(hs.nestLevel - 1));
+         } else {
+            sc.Forward();
          }
-         else if (sc.Match("-}")) {
+      }
+            // Pragma
+      else if (sc.state == SCE_HA_PRAGMA) {
+         if (sc.Match("#-}")) {
+            hs.pragma = false;
+            sc.Forward(3);
+            sc.SetState(SCE_HA_DEFAULT);
+         } else if (sc.Match('-','-')) {
+            sc.SetState(SCE_HA_COMMENTLINE);
             sc.Forward(2);
-            xmode--;
-            if (xmode == 0) {
-               styler.ColourTo(sc.currentPos - 1, sc.state);
-               sc.ChangeState(SCE_HA_DEFAULT);
-            }
+            inDashes = false;
+         } else if (sc.Match('{','-')) {
+            sc.SetState(CommentBlockStyleFromNestLevel(hs.nestLevel));
+            sc.Forward(2);
+            hs.nestLevel = 1;
          } else {
-            if (sc.atLineEnd) {
-                               // Remember the line state for future incremental lexing
-                               styler.SetLineState(lineCurrent, (xmode << 4) | mode);
-                               lineCurrent++;
-                       }
             sc.Forward();
          }
       }
-      // New state?
-      if (sc.state == SCE_HA_DEFAULT) {
+            // New state?
+      else if (sc.state == SCE_HA_DEFAULT) {
          // Digit
-         if (IsADigit(sc.ch) ||
-             (sc.ch == '.' && IsADigit(sc.chNext)) ||
-             (sc.ch == '-' && IsADigit(sc.chNext))) {
-            styler.ColourTo(sc.currentPos - 1, sc.state);
-            sc.ChangeState(SCE_HA_NUMBER);
+         if (IsADigit(sc.ch)) {
+            hs.mode = HA_MODE_DEFAULT;
+
+            sc.SetState(SCE_HA_NUMBER);
             if (sc.ch == '0' && (sc.chNext == 'X' || sc.chNext == 'x')) {
-                               // Match anything starting with "0x" or "0X", too
-                               sc.Forward(2);
-                               xmode = 16;
+               // Match anything starting with "0x" or "0X", too
+               sc.Forward(2);
+               base = 16;
+               dot = false;
             } else if (sc.ch == '0' && (sc.chNext == 'O' || sc.chNext == 'o')) {
-                               // Match anything starting with "0x" or "0X", too
-                               sc.Forward(2);
-                               xmode = 8;
+               // Match anything starting with "0o" or "0O", too
+               sc.Forward(2);
+               base = 8;
+               dot = false;
             } else {
-                               sc.Forward();
-                               xmode = 10;
-                       }
-            mode = HA_MODE_DEFAULT;
+               sc.Forward();
+               base = 10;
+               dot = true;
+            }
+         }
+         // Pragma
+         else if (sc.Match("{-#")) {
+            hs.pragma = true;
+            sc.SetState(SCE_HA_PRAGMA);
+            sc.Forward(3);
          }
          // Comment line
-         else if (sc.Match("--")) {
-            styler.ColourTo(sc.currentPos - 1, sc.state);
+         else if (sc.Match('-','-')) {
+            sc.SetState(SCE_HA_COMMENTLINE);
             sc.Forward(2);
-            sc.ChangeState(SCE_HA_COMMENTLINE);
-         // Comment block
+            inDashes = true;
          }
-         else if (sc.Match("{-")) {
-            styler.ColourTo(sc.currentPos - 1, sc.state);
+         // Comment block
+         else if (sc.Match('{','-')) {
+            sc.SetState(CommentBlockStyleFromNestLevel(hs.nestLevel));
             sc.Forward(2);
-            sc.ChangeState(SCE_HA_COMMENTBLOCK);
-            xmode = 1;
+            hs.nestLevel = 1;
          }
          // String
-         else if (sc.Match('\"')) {
-            styler.ColourTo(sc.currentPos - 1, sc.state);
+         else if (sc.ch == '\"') {
+            sc.SetState(SCE_HA_STRING);
             sc.Forward();
-            sc.ChangeState(SCE_HA_STRING);
          }
-         // Character
-         else if (sc.Match('\'')) {
-            styler.ColourTo(sc.currentPos - 1, sc.state);
+         // Character or quoted name or promoted term
+         else if (sc.ch == '\'') {
+            hs.mode = HA_MODE_DEFAULT;
+
+            sc.SetState(SCE_HA_CHARACTER);
             sc.Forward();
-            sc.ChangeState(SCE_HA_CHARACTER);
-         }
-         else if (sc.ch == '(' || sc.ch == ')' ||
-                  sc.ch == '{' || sc.ch == '}' ||
-                  sc.ch == '[' || sc.ch == ']') {
-                       styler.ColourTo(sc.currentPos - 1, sc.state);
-                       sc.Forward();
-                       styler.ColourTo(sc.currentPos - 1, SCE_HA_OPERATOR);
-                       mode = HA_MODE_DEFAULT;
-                }
+
+            if (options.allowQuotes) {
+               // Quoted type ''T
+               if (sc.ch=='\'' && IsAHaskellWordStart(sc.chNext)) {
+                  sc.Forward();
+                  sc.ChangeState(SCE_HA_IDENTIFIER);
+               } else if (sc.chNext != '\'') {
+                  // Quoted name 'n or promoted constructor 'N
+                  if (IsAHaskellWordStart(sc.ch)) {
+                     sc.ChangeState(SCE_HA_IDENTIFIER);
+                  // Promoted constructor operator ':~>
+                  } else if (sc.ch == ':') {
+                     alreadyInTheMiddleOfOperator = false;
+                     sc.ChangeState(SCE_HA_OPERATOR);
+                  // Promoted list or tuple '[T]
+                  } else if (sc.ch == '[' || sc.ch== '(') {
+                     sc.ChangeState(SCE_HA_OPERATOR);
+                     sc.ForwardSetState(SCE_HA_DEFAULT);
+                  }
+               }
+            }
+         }
+         // Operator starting with '?' or an implicit parameter
+         else if (sc.ch == '?') {
+            hs.mode = HA_MODE_DEFAULT;
+
+            alreadyInTheMiddleOfOperator = false;
+            sc.SetState(SCE_HA_OPERATOR);
+
+            if (  options.implicitParams
+               && IsAHaskellWordStart(sc.chNext)
+               && !IsHaskellUpperCase(sc.chNext)) {
+               sc.Forward();
+               sc.ChangeState(SCE_HA_IDENTIFIER);
+            }
+         }
          // Operator
-         else if (isascii(sc.ch) && isoperator(static_cast<char>(sc.ch))) {
-            styler.ColourTo(sc.currentPos - 1, sc.state);
-            sc.Forward();
-            sc.ChangeState(SCE_HA_OPERATOR);
-            mode = HA_MODE_DEFAULT;
+         else if (IsAnHaskellOperatorChar(sc.ch)) {
+            hs.mode = HA_MODE_DEFAULT;
+
+            sc.SetState(SCE_HA_OPERATOR);
          }
-         // Keyword
-         else if (IsAWordStart(sc.ch)) {
-            styler.ColourTo(sc.currentPos - 1, sc.state);
-            sc.Forward();
-            sc.ChangeState(SCE_HA_IDENTIFIER);
+         // Braces and punctuation
+         else if (sc.ch == ',' || sc.ch == ';'
+               || sc.ch == '(' || sc.ch == ')'
+               || sc.ch == '[' || sc.ch == ']'
+               || sc.ch == '{' || sc.ch == '}') {
+            sc.SetState(SCE_HA_OPERATOR);
+            sc.ForwardSetState(SCE_HA_DEFAULT);
+         }
+         // Keyword or Identifier
+         else if (IsAHaskellWordStart(sc.ch)) {
+            sc.SetState(SCE_HA_IDENTIFIER);
+         // Something we don't care about
          } else {
-            if (sc.atLineEnd) {
-                               // Remember the line state for future incremental lexing
-                               styler.SetLineState(lineCurrent, (xmode << 4) | mode);
-                               lineCurrent++;
-                       }
             sc.Forward();
          }
       }
+            // This branch should never be reached.
+      else {
+         assert(false);
+         sc.Forward();
+      }
    }
    sc.Complete();
 }
 
-// External stuff - used for dynamic-loading, not implemented in wxStyledTextCtrl yet.
-// Inspired by the caml external lexer - Credits to Robert Roessler - http://www.rftp.com
-#ifdef BUILD_EXTERNAL_LEXER
-static const char* LexerName = "haskell";
-
-void EXT_LEXER_DECL Lex(unsigned int lexer, unsigned int startPos, int length, int initStyle,
-                        char *words[], WindowID window, char *props)
-{
-   PropSetSimple ps;
-   ps.SetMultiple(props);
-   WindowAccessor wa(window, ps);
-
-   int nWL = 0;
-   for (; words[nWL]; nWL++) ;
-   WordList** wl = new WordList* [nWL + 1];
-   int i = 0;
-   for (; i<nWL; i++)
-   {
-      wl[i] = new WordList();
-      wl[i]->Set(words[i]);
+void SCI_METHOD LexerHaskell::Fold(unsigned int startPos, int length, int // initStyle
+                                  ,IDocument *pAccess) {
+   if (!options.fold)
+      return;
+
+   Accessor styler(pAccess, NULL);
+
+   int lineCurrent = styler.GetLine(startPos);
+
+   if (lineCurrent <= firstImportLine) {
+      firstImportLine = -1; // readjust first import position
+      firstImportIndent = 0;
    }
-   wl[i] = 0;
 
-   ColorizeHaskellDoc(startPos, length, initStyle, wl, wa);
-   wa.Flush();
-   for (i=nWL-1;i>=0;i--)
-      delete wl[i];
-   delete [] wl;
-}
+   const int maxPos = startPos + length;
+   const int maxLines =
+      maxPos == styler.Length()
+         ? styler.GetLine(maxPos)
+         : styler.GetLine(maxPos - 1);  // Requested last line
+   const int docLines = styler.GetLine(styler.Length()); // Available last line
 
-void EXT_LEXER_DECL Fold (unsigned int lexer, unsigned int startPos, int length, int initStyle,
-                        char *words[], WindowID window, char *props)
-{
+   // Backtrack to previous non-blank line so we can determine indent level
+   // for any white space lines
+   // and so we can fix any preceding fold level (which is why we go back
+   // at least one line in all cases)
+   bool importHere = LineContainsImport(lineCurrent, styler);
+   int indentCurrent = IndentAmountWithOffset(styler, lineCurrent);
 
-}
+   while (lineCurrent > 0) {
+      lineCurrent--;
+      importHere = LineContainsImport(lineCurrent, styler);
+      indentCurrent = IndentAmountWithOffset(styler, lineCurrent);
+      if (!(indentCurrent & SC_FOLDLEVELWHITEFLAG))
+         break;
+   }
 
-int EXT_LEXER_DECL GetLexerCount()
-{
-   return 1;
-}
+   int indentCurrentLevel = indentCurrent & SC_FOLDLEVELNUMBERMASK;
+
+   if (importHere) {
+      indentCurrentLevel = IndentLevelRemoveIndentOffset(indentCurrentLevel);
+      if (firstImportLine == -1) {
+         firstImportLine = lineCurrent;
+         firstImportIndent = (1 + indentCurrentLevel) - SC_FOLDLEVELBASE;
+      }
+      if (firstImportLine != lineCurrent) {
+         indentCurrentLevel++;
+      }
+   }
+
+   indentCurrent = indentCurrentLevel | (indentCurrent & ~SC_FOLDLEVELNUMBERMASK);
+
+   // Process all characters to end of requested range
+   //that hangs over the end of the range.  Cap processing in all cases
+   // to end of document.
+   while (lineCurrent <= docLines && lineCurrent <= maxLines) {
+
+      // Gather info
+      int lineNext = lineCurrent + 1;
+      importHere = false;
+      int indentNext = indentCurrent;
+
+      if (lineNext <= docLines) {
+         // Information about next line is only available if not at end of document
+         importHere = LineContainsImport(lineNext, styler);
+         indentNext = IndentAmountWithOffset(styler, lineNext);
+      }
+      if (indentNext & SC_FOLDLEVELWHITEFLAG)
+         indentNext = SC_FOLDLEVELWHITEFLAG | indentCurrentLevel;
+
+      // Skip past any blank lines for next indent level info; we skip also
+      // comments (all comments, not just those starting in column 0)
+      // which effectively folds them into surrounding code rather
+      // than screwing up folding.
+
+      while (lineNext < docLines && (indentNext & SC_FOLDLEVELWHITEFLAG)) {
+         lineNext++;
+         importHere = LineContainsImport(lineNext, styler);
+         indentNext = IndentAmountWithOffset(styler, lineNext);
+      }
+
+      int indentNextLevel = indentNext & SC_FOLDLEVELNUMBERMASK;
+
+      if (importHere) {
+         indentNextLevel = IndentLevelRemoveIndentOffset(indentNextLevel);
+         if (firstImportLine == -1) {
+            firstImportLine = lineNext;
+            firstImportIndent = (1 + indentNextLevel) - SC_FOLDLEVELBASE;
+         }
+         if (firstImportLine != lineNext) {
+            indentNextLevel++;
+         }
+      }
+
+      indentNext = indentNextLevel | (indentNext & ~SC_FOLDLEVELNUMBERMASK);
+
+      const int levelBeforeComments = Maximum(indentCurrentLevel,indentNextLevel);
+
+      // Now set all the indent levels on the lines we skipped
+      // Do this from end to start.  Once we encounter one line
+      // which is indented more than the line after the end of
+      // the comment-block, use the level of the block before
 
-void EXT_LEXER_DECL GetLexerName(unsigned int Index, char *name, int buflength)
-{
-   if (buflength > 0) {
-      buflength--;
-      int n = strlen(LexerName);
-      if (n > buflength)
-         n = buflength;
-      memcpy(name, LexerName, n), name[n] = '\0';
+      int skipLine = lineNext;
+      int skipLevel = indentNextLevel;
+
+      while (--skipLine > lineCurrent) {
+         int skipLineIndent = IndentAmountWithOffset(styler, skipLine);
+
+         if (options.foldCompact) {
+            if ((skipLineIndent & SC_FOLDLEVELNUMBERMASK) > indentNextLevel) {
+               skipLevel = levelBeforeComments;
+            }
+
+            int whiteFlag = skipLineIndent & SC_FOLDLEVELWHITEFLAG;
+
+            styler.SetLevel(skipLine, skipLevel | whiteFlag);
+         } else {
+            if (  (skipLineIndent & SC_FOLDLEVELNUMBERMASK) > indentNextLevel
+               && !(skipLineIndent & SC_FOLDLEVELWHITEFLAG)) {
+               skipLevel = levelBeforeComments;
+            }
+
+            styler.SetLevel(skipLine, skipLevel);
+         }
+      }
+
+      int lev = indentCurrent;
+
+      if (!(indentCurrent & SC_FOLDLEVELWHITEFLAG)) {
+         if ((indentCurrent & SC_FOLDLEVELNUMBERMASK) < (indentNext & SC_FOLDLEVELNUMBERMASK))
+            lev |= SC_FOLDLEVELHEADERFLAG;
+      }
+
+      // Set fold level for this line and move to next line
+      styler.SetLevel(lineCurrent, options.foldCompact ? lev : lev & ~SC_FOLDLEVELWHITEFLAG);
+
+      indentCurrent = indentNext;
+      indentCurrentLevel = indentNextLevel;
+      lineCurrent = lineNext;
    }
+
+   // NOTE: Cannot set level of last line here because indentCurrent doesn't have
+   // header flag set; the loop above is crafted to take care of this case!
+   //styler.SetLevel(lineCurrent, indentCurrent);
 }
-#endif
 
-LexerModule lmHaskell(SCLEX_HASKELL, ColorizeHaskellDoc, "haskell");
+LexerModule lmHaskell(SCLEX_HASKELL, LexerHaskell::LexerFactoryHaskell, "haskell", haskellWordListDesc);
+LexerModule lmLiterateHaskell(SCLEX_LITERATEHASKELL, LexerHaskell::LexerFactoryLiterateHaskell, 
"literatehaskell", haskellWordListDesc);
diff --git a/plugins/scintilla/scintilla/lexers/LexLaTeX.cxx b/plugins/scintilla/scintilla/lexers/LexLaTeX.cxx
index 6f9612d..f3b1405 100644
--- a/plugins/scintilla/scintilla/lexers/LexLaTeX.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexLaTeX.cxx
@@ -224,7 +224,7 @@ void SCI_METHOD LexerLaTeX::Lex(unsigned int startPos, int length, int initStyle
                                        chNext = styler.SafeGetCharAt(i + 1);
                                } else if (chNext == '\r' || chNext == '\n') {
                                        styler.ColourTo(i, SCE_L_ERROR);
-                               } else {
+                               } else if (isascii(chNext)) {
                                        styler.ColourTo(i + 1, SCE_L_SHORTCMD);
                                        if (chNext == '(') {
                                                mode = 1;
@@ -340,7 +340,7 @@ void SCI_METHOD LexerLaTeX::Lex(unsigned int startPos, int length, int initStyle
                                        chNext = styler.SafeGetCharAt(i + 1);
                                } else if (chNext == '\r' || chNext == '\n') {
                                        styler.ColourTo(i, SCE_L_ERROR);
-                               } else {
+                               } else if (isascii(chNext)) {
                                        if (chNext == ')') {
                                                mode = 0;
                                                state = SCE_L_DEFAULT;
@@ -382,7 +382,7 @@ void SCI_METHOD LexerLaTeX::Lex(unsigned int startPos, int length, int initStyle
                                        chNext = styler.SafeGetCharAt(i + 1);
                                } else if (chNext == '\r' || chNext == '\n') {
                                        styler.ColourTo(i, SCE_L_ERROR);
-                               } else {
+                               } else if (isascii(chNext)) {
                                        if (chNext == ']') {
                                                mode = 0;
                                                state = SCE_L_DEFAULT;
diff --git a/plugins/scintilla/scintilla/lexers/LexLua.cxx b/plugins/scintilla/scintilla/lexers/LexLua.cxx
index 4277d87..62bb44d 100644
--- a/plugins/scintilla/scintilla/lexers/LexLua.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexLua.cxx
@@ -132,55 +132,38 @@ static void ColouriseLuaDoc(
                if (sc.state == SCE_LUA_OPERATOR) {
                        if (sc.ch == ':' && sc.chPrev == ':') { // :: <label> :: forward scan
                                sc.Forward();
-                               int ln = 0, maxln = startPos + length - sc.currentPos;
-                               int c;
-                               while (ln < maxln) {            // determine line extent
-                                       c = sc.GetRelative(ln);
-                                       if (c == '\r' || c == '\n')
-                                               break;
-                                       ln++;
-                               }
-                               maxln = ln; ln = 0;
-                               while (ln < maxln) {            // skip over spaces/tabs
-                                       if (!IsASpaceOrTab(sc.GetRelative(ln)))
-                                               break;
+                               int ln = 0;
+                               while (IsASpaceOrTab(sc.GetRelative(ln)))       // skip over spaces/tabs
                                        ln++;
-                               }
                                int ws1 = ln;
                                if (setWordStart.Contains(sc.GetRelative(ln))) {
-                                       int i = 0;
+                                       int c, i = 0;
                                        char s[100];
-                                       while (ln < maxln) {    // get potential label
-                                               c = sc.GetRelative(ln);
-                                               if (!setWord.Contains(c))
-                                                       break;
+                                       while (setWord.Contains(c = sc.GetRelative(ln))) {      // get 
potential label
                                                if (i < 90)
                                                        s[i++] = c;
                                                ln++;
                                        }
                                        s[i] = '\0'; int lbl = ln;
                                        if (!keywords.InList(s)) {
-                                               while (ln < maxln) {            // skip over spaces/tabs
-                                                       if (!IsASpaceOrTab(sc.GetRelative(ln)))
-                                                               break;
+                                               while (IsASpaceOrTab(sc.GetRelative(ln)))       // skip over 
spaces/tabs
                                                        ln++;
-                                               }
                                                int ws2 = ln - lbl;
                                                if (sc.GetRelative(ln) == ':' && sc.GetRelative(ln + 1) == 
':') {
                                                        // final :: found, complete valid label construct
                                                        sc.ChangeState(SCE_LUA_LABEL);
                                                        if (ws1) {
                                                                sc.SetState(SCE_LUA_DEFAULT);
-                                                               sc.Forward(ws1);
+                                                               sc.ForwardBytes(ws1);
                                                        }
                                                        sc.SetState(SCE_LUA_LABEL);
-                                                       sc.Forward(lbl - ws1);
+                                                       sc.ForwardBytes(lbl - ws1);
                                                        if (ws2) {
                                                                sc.SetState(SCE_LUA_DEFAULT);
-                                                               sc.Forward(ws2);
+                                                               sc.ForwardBytes(ws2);
                                                        }
                                                        sc.SetState(SCE_LUA_LABEL);
-                                                       sc.Forward(2);
+                                                       sc.ForwardBytes(2);
                                                }
                                        }
                                }
diff --git a/plugins/scintilla/scintilla/lexers/LexMatlab.cxx 
b/plugins/scintilla/scintilla/lexers/LexMatlab.cxx
index 68915af..c59b8f9 100644
--- a/plugins/scintilla/scintilla/lexers/LexMatlab.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexMatlab.cxx
@@ -6,6 +6,12 @@
  ** Changes by Christoph Dalitz 2003/12/04:
  **   - added support for Octave
  **   - Strings can now be included both in single or double quotes
+ **
+ ** Changes by John Donoghue 2012/04/02
+ **   - added block comment (and nested block comments)
+ **   - added ... displayed as a comment
+ **   - removed unused IsAWord functions
+ **   - added some comments
  **/
 // Copyright 1998-2001 by Neil Hodgson <neilh scintilla org>
 // The License.txt file describes the conditions under which this software may be distributed.
@@ -48,14 +54,6 @@ static bool IsOctaveComment(Accessor &styler, int pos, int len) {
        return len > 0 && IsOctaveCommentChar(styler[pos]) ;
 }
 
-static inline bool IsAWordChar(const int ch) {
-       return (ch < 0x80) && (isalnum(ch) || ch == '_');
-}
-
-static inline bool IsAWordStart(const int ch) {
-       return (ch < 0x80) && (isalnum(ch) || ch == '_');
-}
-
 static void ColouriseMatlabOctaveDoc(
             unsigned int startPos, int length, int initStyle,
             WordList *keywordlists[], Accessor &styler,
@@ -65,12 +63,41 @@ static void ColouriseMatlabOctaveDoc(
 
        styler.StartAt(startPos);
 
+       // boolean for when the ' is allowed to be transpose vs the start/end 
+       // of a string
        bool transpose = false;
 
+       // approximate position of first non space character in a line
+       int nonSpaceColumn = -1;
+       // approximate column position of the current character in a line
+       int column = 0;
+
+        // use the line state of each line to store the block comment depth
+       int curLine = styler.GetLine(startPos);
+        int commentDepth = curLine > 0 ? styler.GetLineState(curLine-1) : 0;
+
+
        StyleContext sc(startPos, length, initStyle, styler);
 
-       for (; sc.More(); sc.Forward()) {
+       for (; sc.More(); sc.Forward(), column++) {
+
+                       if(sc.atLineStart) {
+                       // set the line state to the current commentDepth 
+                       curLine = styler.GetLine(sc.currentPos);
+                        styler.SetLineState(curLine, commentDepth);
 
+                       // reset the column to 0, nonSpace to -1 (not set)
+                       column = 0;
+                       nonSpaceColumn = -1; 
+               }
+
+               // save the column position of first non space character in a line
+               if((nonSpaceColumn == -1) && (! IsASpace(sc.ch)))
+               {
+                       nonSpaceColumn = column;
+               }
+
+               // check for end of states
                if (sc.state == SCE_MATLAB_OPERATOR) {
                        if (sc.chPrev == '.') {
                                if (sc.ch == '*' || sc.ch == '/' || sc.ch == '\\' || sc.ch == '^') {
@@ -79,6 +106,10 @@ static void ColouriseMatlabOctaveDoc(
                                } else if (sc.ch == '\'') {
                                        sc.ForwardSetState(SCE_MATLAB_DEFAULT);
                                        transpose = true;
+                                } else if(sc.ch == '.' && sc.chNext == '.') {
+                                        // we werent an operator, but a '...' 
+                                        sc.ChangeState(SCE_MATLAB_COMMENT);
+                                        transpose = false;
                                } else {
                                        sc.SetState(SCE_MATLAB_DEFAULT);
                                }
@@ -121,15 +152,51 @@ static void ColouriseMatlabOctaveDoc(
                        } else if (sc.ch == '\"') {
                                sc.ForwardSetState(SCE_MATLAB_DEFAULT);
                        }
-               } else if (sc.state == SCE_MATLAB_COMMENT || sc.state == SCE_MATLAB_COMMAND) {
+               } else if (sc.state == SCE_MATLAB_COMMAND) {
                        if (sc.atLineEnd) {
                                sc.SetState(SCE_MATLAB_DEFAULT);
                                transpose = false;
                        }
+               } else if (sc.state == SCE_MATLAB_COMMENT) {
+                       // end or start of a nested a block comment?
+                       if( IsCommentChar(sc.ch) && sc.chNext == '}' && nonSpaceColumn == column) {
+                               if(commentDepth > 0) commentDepth --;
+ 
+                               curLine = styler.GetLine(sc.currentPos);
+                               styler.SetLineState(curLine, commentDepth);
+                               sc.Forward();
+
+                               if (commentDepth == 0) {
+                                       sc.ForwardSetState(SCE_D_DEFAULT);
+                                       transpose = false;
+                               }
+                        }
+                        else if( IsCommentChar(sc.ch) && sc.chNext == '{' && nonSpaceColumn == column)
+                        {
+                               commentDepth ++;
+
+                               curLine = styler.GetLine(sc.currentPos);
+                               styler.SetLineState(curLine, commentDepth);
+                               sc.Forward();
+                               transpose = false;
+
+                        } else if(commentDepth == 0) {
+                               // single line comment
+                               if (sc.atLineEnd || sc.ch == '\r' || sc.ch == '\n') {
+                                       sc.SetState(SCE_MATLAB_DEFAULT);
+                                       transpose = false;
+                               }
+                       }
                }
 
+               // check start of a new state
                if (sc.state == SCE_MATLAB_DEFAULT) {
                        if (IsCommentChar(sc.ch)) {
+                               // ncrement depth if we are a block comment
+                               if(sc.chNext == '{' && nonSpaceColumn == column)
+                                       commentDepth ++;
+                               curLine = styler.GetLine(sc.currentPos);
+                               styler.SetLineState(curLine, commentDepth);
                                sc.SetState(SCE_MATLAB_COMMENT);
                        } else if (sc.ch == '!' && sc.chNext != '=' ) {
                                sc.SetState(SCE_MATLAB_COMMAND);
diff --git a/plugins/scintilla/scintilla/lexers/LexModula.cxx 
b/plugins/scintilla/scintilla/lexers/LexModula.cxx
index cc5847f..ed61560 100644
--- a/plugins/scintilla/scintilla/lexers/LexModula.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexModula.cxx
@@ -63,16 +63,16 @@ static inline unsigned IsOperator( StyleContext & sc, WordList & op ) {
        s[0] = sc.ch;
        s[1] = sc.chNext;
        s[2] = 0;
-       for( i = 0; i < op.len; i++ ) {
-               if( ( strlen( op.words[i] ) == 2 ) &&
-                       ( s[0] == op.words[i][0] && s[1] == op.words[i][1] ) ) {
+       for( i = 0; i < op.Length(); i++ ) {
+               if( ( strlen( op.WordAt(i) ) == 2 ) &&
+                       ( s[0] == op.WordAt(i)[0] && s[1] == op.WordAt(i)[1] ) ) {
                        return 2;
                }
        }
        s[1] = 0;
-       for( i = 0; i < op.len; i++ ) {
-               if( ( strlen( op.words[i] ) == 1 ) &&
-                       ( s[0] == op.words[i][0] ) ) {
+       for( i = 0; i < op.Length(); i++ ) {
+               if( ( strlen( op.WordAt(i) ) == 1 ) &&
+                       ( s[0] == op.WordAt(i)[0] ) ) {
                        return 1;
                }
        }
diff --git a/plugins/scintilla/scintilla/lexers/LexOthers.cxx 
b/plugins/scintilla/scintilla/lexers/LexOthers.cxx
index 8299781..8015af1 100644
--- a/plugins/scintilla/scintilla/lexers/LexOthers.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexOthers.cxx
@@ -922,8 +922,9 @@ static int RecogniseErrorListLine(const char *lineBuffer, unsigned int lengthLin
                (strstr(lineBuffer, " at ") < (lineBuffer + lengthLine)) &&
                   strstr(lineBuffer, " line ") &&
                   (strstr(lineBuffer, " line ") < (lineBuffer + lengthLine)) &&
-               (strstr(lineBuffer, " at ") < (strstr(lineBuffer, " line ")))) {
-               // perl error message
+               (strstr(lineBuffer, " at ") + 4 < (strstr(lineBuffer, " line ")))) {
+               // perl error message:
+               // <message> at <file> line <line>
                return SCE_ERR_PERL;
        } else if ((memcmp(lineBuffer, "   at ", 6) == 0) &&
                   strstr(lineBuffer, ":line ")) {
@@ -1047,10 +1048,10 @@ static int RecogniseErrorListLine(const char *lineBuffer, unsigned int lengthLin
                                }
                        } else if (state == stCtagsStart) {
                                if ((lineBuffer[i - 1] == '\t') &&
-                                       ((ch == '/' && lineBuffer[i + 1] == '^') || Is0To9(ch))) {
+                                       ((ch == '/' && chNext == '^') || Is0To9(ch))) {
                                        state = stCtags;
                                        break;
-                               } else if ((ch == '/') && (lineBuffer[i + 1] == '^')) {
+                               } else if ((ch == '/') && (chNext == '^')) {
                                        state = stCtagsStartString;
                                }
                        } else if ((state == stCtagsStartString) && ((lineBuffer[i] == '$') && (lineBuffer[i 
+ 1] == '/'))) {
diff --git a/plugins/scintilla/scintilla/lexers/LexPerl.cxx b/plugins/scintilla/scintilla/lexers/LexPerl.cxx
index da90387..de47474 100644
--- a/plugins/scintilla/scintilla/lexers/LexPerl.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexPerl.cxx
@@ -188,22 +188,6 @@ static int styleCheckIdentifier(LexAccessor &styler, unsigned int bk) {
        return 0;
 }
 
-static int inputsymbolScan(LexAccessor &styler, unsigned int pos, unsigned int endPos) {
-       // looks forward for matching > on same line; a bit ugly
-       unsigned int fw = pos;
-       while (++fw < endPos) {
-               int fwch = static_cast<unsigned char>(styler.SafeGetCharAt(fw));
-               if (fwch == '\r' || fwch == '\n') {
-                       return 0;
-               } else if (fwch == '>') {
-                       if (styler.Match(fw - 2, "<=>"))        // '<=>' case
-                               return 0;
-                       return fw - pos;
-               }
-       }
-       return 0;
-}
-
 static int podLineScan(LexAccessor &styler, unsigned int &pos, unsigned int endPos) {
        // forward scan the current line to classify line for POD style
        int state = -1;
@@ -398,6 +382,7 @@ public:
        static ILexer *LexerFactoryPerl() {
                return new LexerPerl();
        }
+       int InputSymbolScan(StyleContext &sc);
        void InterpolateSegment(StyleContext &sc, int maxSeg, bool isPattern=false);
 };
 
@@ -427,6 +412,21 @@ int SCI_METHOD LexerPerl::WordListSet(int n, const char *wl) {
        return firstModification;
 }
 
+int LexerPerl::InputSymbolScan(StyleContext &sc) {
+       // forward scan for matching > on same line; file handles
+       int c, sLen = 0;
+       while ((c = sc.GetRelativeCharacter(++sLen)) != 0) {
+               if (c == '\r' || c == '\n') {
+                       return 0;
+               } else if (c == '>') {
+                       if (sc.Match("<=>"))    // '<=>' case
+                               return 0;
+                       return sLen;
+               }
+       }
+       return 0;
+}
+
 void LexerPerl::InterpolateSegment(StyleContext &sc, int maxSeg, bool isPattern) {
        // interpolate a segment (with no active backslashes or delimiters within)
        // switch in or out of an interpolation style or continue current style
@@ -441,39 +441,42 @@ void LexerPerl::InterpolateSegment(StyleContext &sc, int maxSeg, bool isPattern)
                        if (sc.ch == '$' && sc.chNext == '#') { // starts with $#
                                sLen++;
                        }
-                       while ((maxSeg > sLen) && (sc.GetRelative(sLen) == '$'))        // >0 $ dereference 
within
+                       while ((maxSeg > sLen) && (sc.GetRelativeCharacter(sLen) == '$'))       // >0 $ 
dereference within
                                sLen++;
-                       if ((maxSeg > sLen) && (sc.GetRelative(sLen) == '{')) { // { start for {word}
+                       if ((maxSeg > sLen) && (sc.GetRelativeCharacter(sLen) == '{')) {        // { start 
for {word}
                                sLen++;
                                braces = true;
                        }
                        if (maxSeg > sLen) {
-                               int c = sc.GetRelative(sLen);
+                               int c = sc.GetRelativeCharacter(sLen);
                                if (setWordStart.Contains(c)) { // word (various)
                                        sLen++;
                                        isVar = true;
-                                       while ((maxSeg > sLen) && setWord.Contains(sc.GetRelative(sLen)))
+                                       while (maxSeg > sLen) {
+                                               if (!setWord.Contains(sc.GetRelativeCharacter(sLen)))
+                                                       break;
                                                sLen++;
+                                       }
                                } else if (braces && IsADigit(c) && (sLen == 2)) {      // digit for ${digit}
                                        sLen++;
                                        isVar = true;
                                }
                        }
                        if (braces) {
-                               if ((maxSeg > sLen) && (sc.GetRelative(sLen) == '}')) { // } end for {word}
+                               if ((maxSeg > sLen) && (sc.GetRelativeCharacter(sLen) == '}')) {        // } 
end for {word}
                                        sLen++;
                                } else
                                        isVar = false;
                        }
                }
                if (!isVar && (maxSeg > 1)) {   // $- or @-specific variable patterns
-                       sLen = 1;
                        int c = sc.chNext;
                        if (sc.ch == '$') {
+                               sLen = 1;
                                if (IsADigit(c)) {      // $[0-9] and slurp trailing digits
                                        sLen++;
                                        isVar = true;
-                                       while ((maxSeg > sLen) && IsADigit(sc.GetRelative(sLen)))
+                                       while ((maxSeg > sLen) && IsADigit(sc.GetRelativeCharacter(sLen)))
                                                sLen++;
                                } else if (setSpecialVar.Contains(c)) { // $ special variables
                                        sLen++;
@@ -483,12 +486,13 @@ void LexerPerl::InterpolateSegment(StyleContext &sc, int maxSeg, bool isPattern)
                                        isVar = true;
                                } else if (c == '^') {  // $^A control-char style
                                        sLen++;
-                                       if ((maxSeg > sLen) && setControlVar.Contains(sc.GetRelative(sLen))) {
+                                       if ((maxSeg > sLen) && 
setControlVar.Contains(sc.GetRelativeCharacter(sLen))) {
                                                sLen++;
                                                isVar = true;
                                        }
                                }
                        } else if (sc.ch == '@') {
+                               sLen = 1;
                                if (!isPattern && ((c == '+') || (c == '-'))) { // @ specials non-pattern
                                        sLen++;
                                        isVar = true;
@@ -576,7 +580,7 @@ void SCI_METHOD LexerPerl::Lex(unsigned int startPos, int length, int initStyle,
                int Count;
                int Up, Down;
                QuoteCls() {
-                       this->New(1);
+                       New(1);
                }
                void New(int r = 1) {
                        Rep   = r;
@@ -896,19 +900,18 @@ void SCI_METHOD LexerPerl::Lex(unsigned int startPos, int length, int initStyle,
                                break;
                        }
                        while (!sc.atLineEnd) {         // "EOF" and `EOF` interpolated
-                               int s = 0, endType = 0;
-                               int maxSeg = endPos - sc.currentPos;
-                               while (s < maxSeg) {    // scan to break string into segments
-                                       int c = sc.GetRelative(s);
+                               int c, sLen = 0, endType = 0;
+                               while ((c = sc.GetRelativeCharacter(sLen)) != 0) {
+                                       // scan to break string into segments
                                        if (c == '\\') {
                                                endType = 1; break;
                                        } else if (c == '\r' || c == '\n') {
                                                endType = 2; break;
                                        }
-                                       s++;
+                                       sLen++;
                                }
-                               if (s > 0)      // process non-empty segments
-                                       InterpolateSegment(sc, s);
+                               if (sLen > 0)   // process non-empty segments
+                                       InterpolateSegment(sc, sLen);
                                if (endType == 1) {
                                        sc.Forward();
                                        // \ at end-of-line does not appear to have any effect, skip
@@ -969,10 +972,9 @@ void SCI_METHOD LexerPerl::Lex(unsigned int startPos, int length, int initStyle,
                        } else if (!Quote.Up && !IsASpace(sc.ch)) {
                                Quote.Open(sc.ch);
                        } else {
-                               int s = 0, endType = 0;
-                               int maxSeg = endPos - sc.currentPos;
-                               while (s < maxSeg) {    // scan to break string into segments
-                                       int c = sc.GetRelative(s);
+                               int c, sLen = 0, endType = 0;
+                               while ((c = sc.GetRelativeCharacter(sLen)) != 0) {
+                                       // scan to break string into segments
                                        if (IsASpace(c)) {
                                                break;
                                        } else if (c == '\\' && Quote.Up != '\\') {
@@ -985,13 +987,13 @@ void SCI_METHOD LexerPerl::Lex(unsigned int startPos, int length, int initStyle,
                                                }
                                        } else if (c == Quote.Up)
                                                Quote.Count++;
-                                       s++;
+                                       sLen++;
                                }
-                               if (s > 0) {    // process non-empty segments
+                               if (sLen > 0) { // process non-empty segments
                                        if (Quote.Up != '\'') {
-                                               InterpolateSegment(sc, s, true);
+                                               InterpolateSegment(sc, sLen, true);
                                        } else          // non-interpolated path
-                                               sc.Forward(s);
+                                               sc.Forward(sLen);
                                }
                                if (endType == 1)
                                        sc.Forward();
@@ -1005,11 +1007,10 @@ void SCI_METHOD LexerPerl::Lex(unsigned int startPos, int length, int initStyle,
                        } else if (!Quote.Up && !IsASpace(sc.ch)) {
                                Quote.Open(sc.ch);
                        } else {
-                               int s = 0, endType = 0;
-                               int maxSeg = endPos - sc.currentPos;
+                               int c, sLen = 0, endType = 0;
                                bool isPattern = (Quote.Rep == 2);
-                               while (s < maxSeg) {    // scan to break string into segments
-                                       int c = sc.GetRelative(s);
+                               while ((c = sc.GetRelativeCharacter(sLen)) != 0) {
+                                       // scan to break string into segments
                                        if (c == '\\' && Quote.Up != '\\') {
                                                endType = 2; break;
                                        } else if (Quote.Count == 0 && Quote.Rep == 1) {
@@ -1020,7 +1021,7 @@ void SCI_METHOD LexerPerl::Lex(unsigned int startPos, int length, int initStyle,
                                                // For '#', if no whitespace in between, it's a delimiter.
                                                if (IsASpace(c)) {
                                                        // Keep going
-                                               } else if (c == '#' && IsASpaceOrTab(sc.GetRelative(s - 1))) {
+                                               } else if (c == '#' && IsASpaceOrTab(sc.GetRelative(sLen - 
1))) {
                                                        endType = 3;
                                                } else
                                                        Quote.Open(c);
@@ -1039,13 +1040,13 @@ void SCI_METHOD LexerPerl::Lex(unsigned int startPos, int length, int initStyle,
                                                Quote.Count++;
                                        } else if (IsASpace(c))
                                                break;
-                                       s++;
+                                       sLen++;
                                }
-                               if (s > 0) {    // process non-empty segments
+                               if (sLen > 0) { // process non-empty segments
                                        if (sc.state == SCE_PL_REGSUBST && Quote.Up != '\'') {
-                                               InterpolateSegment(sc, s, isPattern);
+                                               InterpolateSegment(sc, sLen, isPattern);
                                        } else          // non-interpolated path
-                                               sc.Forward(s);
+                                               sc.Forward(sLen);
                                }
                                if (endType == 2) {
                                        sc.Forward();
@@ -1063,10 +1064,9 @@ void SCI_METHOD LexerPerl::Lex(unsigned int startPos, int length, int initStyle,
                        if (!Quote.Down && !IsASpace(sc.ch)) {
                                Quote.Open(sc.ch);
                        } else {
-                               int s = 0, endType = 0;
-                               int maxSeg = endPos - sc.currentPos;
-                               while (s < maxSeg) {    // scan to break string into segments
-                                       int c = sc.GetRelative(s);
+                               int c, sLen = 0, endType = 0;
+                               while ((c = sc.GetRelativeCharacter(sLen)) != 0) {
+                                       // scan to break string into segments
                                        if (IsASpace(c)) {
                                                break;
                                        } else if (c == '\\' && Quote.Up != '\\') {
@@ -1078,23 +1078,23 @@ void SCI_METHOD LexerPerl::Lex(unsigned int startPos, int length, int initStyle,
                                                }
                                        } else if (c == Quote.Up)
                                                Quote.Count++;
-                                       s++;
+                                       sLen++;
                                }
-                               if (s > 0) {    // process non-empty segments
+                               if (sLen > 0) { // process non-empty segments
                                        switch (sc.state) {
                                        case SCE_PL_STRING:
                                        case SCE_PL_STRING_QQ:
                                        case SCE_PL_BACKTICKS:
-                                               InterpolateSegment(sc, s);
+                                               InterpolateSegment(sc, sLen);
                                                break;
                                        case SCE_PL_STRING_QX:
                                                if (Quote.Up != '\'') {
-                                                       InterpolateSegment(sc, s);
+                                                       InterpolateSegment(sc, sLen);
                                                        break;
                                                }
                                                // (continued for ' delim)
                                        default:        // non-interpolated path
-                                               sc.Forward(s);
+                                               sc.Forward(sLen);
                                        }
                                }
                                if (endType == 2) {
@@ -1474,7 +1474,7 @@ void SCI_METHOD LexerPerl::Lex(unsigned int startPos, int length, int initStyle,
                                } else if (sc.ch == '<') {      // handle '<', inputsymbol
                                        if (preferRE) {
                                                // forward scan
-                                               int i = inputsymbolScan(styler, sc.currentPos, endPos);
+                                               int i = InputSymbolScan(sc);
                                                if (i > 0) {
                                                        sc.SetState(SCE_PL_IDENTIFIER);
                                                        sc.Forward(i);
diff --git a/plugins/scintilla/scintilla/lexers/LexPowerShell.cxx 
b/plugins/scintilla/scintilla/lexers/LexPowerShell.cxx
index 7f741fc..1b568c0 100644
--- a/plugins/scintilla/scintilla/lexers/LexPowerShell.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexPowerShell.cxx
@@ -40,6 +40,7 @@ static void ColourisePowerShellDoc(unsigned int startPos, int length, int initSt
        WordList &keywords3 = *keywordlists[2];
        WordList &keywords4 = *keywordlists[3];
        WordList &keywords5 = *keywordlists[4];
+       WordList &keywords6 = *keywordlists[5];
 
        styler.StartAt(startPos);
 
@@ -52,9 +53,26 @@ static void ColourisePowerShellDoc(unsigned int startPos, int length, int initSt
                                sc.SetState(SCE_POWERSHELL_DEFAULT);
                        }
                } else if (sc.state == SCE_POWERSHELL_COMMENTSTREAM) {
+                       if(sc.atLineStart) {
+                               while(IsASpaceOrTab(sc.ch)) {
+                                       sc.Forward();
+                               }
+                               if (sc.ch == '.' && IsAWordChar(sc.chNext)) {
+                                       sc.SetState(SCE_POWERSHELL_COMMENTDOCKEYWORD);
+                               }
+                       }
                        if (sc.ch == '>' && sc.chPrev == '#') {
                                sc.ForwardSetState(SCE_POWERSHELL_DEFAULT);
                        }
+               } else if (sc.state == SCE_POWERSHELL_COMMENTDOCKEYWORD) {
+                       if(!IsAWordChar(sc.ch)) {
+                               char s[100];
+                               sc.GetCurrentLowered(s, sizeof(s));
+                               if (!keywords6.InList(s + 1)) {
+                                       sc.ChangeState(SCE_POWERSHELL_COMMENTSTREAM);
+                               }
+                               sc.SetState(SCE_POWERSHELL_COMMENTSTREAM);
+                       }
                } else if (sc.state == SCE_POWERSHELL_STRING) {
                        // This is a doubles quotes string
                        if (sc.ch == '\"') {
@@ -65,6 +83,18 @@ static void ColourisePowerShellDoc(unsigned int startPos, int length, int initSt
                        if (sc.ch == '\'') {
                                sc.ForwardSetState(SCE_POWERSHELL_DEFAULT);
                        }
+               } else if (sc.state == SCE_POWERSHELL_HERE_STRING) {
+                       // This is a doubles quotes here-string
+                       if (sc.atLineStart && sc.ch == '\"' && sc.chNext == '@') {
+                               sc.Forward(2);
+                               sc.SetState(SCE_POWERSHELL_DEFAULT);
+                       }
+               } else if (sc.state == SCE_POWERSHELL_HERE_CHARACTER) {
+                       // This is a single quote here-string
+                       if (sc.atLineStart && sc.ch == '\'' && sc.chNext == '@') {
+                               sc.Forward(2);
+                               sc.SetState(SCE_POWERSHELL_DEFAULT);
+                       }
                } else if (sc.state == SCE_POWERSHELL_NUMBER) {
                        if (!IsADigit(sc.ch)) {
                                sc.SetState(SCE_POWERSHELL_DEFAULT);
@@ -107,6 +137,10 @@ static void ColourisePowerShellDoc(unsigned int startPos, int length, int initSt
                                sc.SetState(SCE_POWERSHELL_STRING);
                        } else if (sc.ch == '\'') {
                                sc.SetState(SCE_POWERSHELL_CHARACTER);
+                       } else if (sc.ch == '@' && sc.chNext == '\"') {
+                               sc.SetState(SCE_POWERSHELL_HERE_STRING);
+                       } else if (sc.ch == '@' && sc.chNext == '\'') {
+                               sc.SetState(SCE_POWERSHELL_HERE_CHARACTER);
                        } else if (sc.ch == '$') {
                                sc.SetState(SCE_POWERSHELL_VARIABLE);
                        } else if (IsADigit(sc.ch) || (sc.ch == '.' && IsADigit(sc.chNext))) {
@@ -159,11 +193,23 @@ static void FoldPowerShellDoc(unsigned int startPos, int length, int initStyle,
                                levelNext--;
                        }
                } else if (foldComment && style == SCE_POWERSHELL_COMMENTSTREAM) {
-                       if (stylePrev != SCE_POWERSHELL_COMMENTSTREAM) {
+                       if (stylePrev != SCE_POWERSHELL_COMMENTSTREAM && stylePrev != 
SCE_POWERSHELL_COMMENTDOCKEYWORD) {
                                levelNext++;
-                       } else if (styleNext != SCE_POWERSHELL_COMMENTSTREAM) {
+                       } else if (styleNext != SCE_POWERSHELL_COMMENTSTREAM && styleNext != 
SCE_POWERSHELL_COMMENTDOCKEYWORD) {
                                levelNext--;
                        }
+               } else if (foldComment && style == SCE_POWERSHELL_COMMENT) {
+                       if (ch == '#') {
+                               unsigned int j = i + 1;
+                               while ((j < endPos) && IsASpaceOrTab(styler.SafeGetCharAt(j))) {
+                                       j++;
+                               }
+                               if (styler.Match(j, "region")) {
+                                       levelNext++;
+                               } else if (styler.Match(j, "endregion")) {
+                                       levelNext--;
+                               }
+                       }
                }
                if (!IsASpace(ch))
                        visibleChars++;
@@ -194,6 +240,7 @@ static const char * const powershellWordLists[] = {
        "Aliases",
        "Functions",
        "User1",
+       "DocComment",
        0
 };
 
diff --git a/plugins/scintilla/scintilla/lexers/LexRuby.cxx b/plugins/scintilla/scintilla/lexers/LexRuby.cxx
index 40424aa..833ad59 100644
--- a/plugins/scintilla/scintilla/lexers/LexRuby.cxx
+++ b/plugins/scintilla/scintilla/lexers/LexRuby.cxx
@@ -119,7 +119,7 @@ static int ClassifyWordRb(unsigned int start, unsigned int end, WordList &keywor
                chAttr = SCE_RB_MODULE_NAME;
        else if (0 == strcmp(prevWord, "def"))
                chAttr = SCE_RB_DEFNAME;
-    else if (keywords.InList(s) && !followsDot(start - 1, styler)) {
+    else if (keywords.InList(s) && ((start == 0) || !followsDot(start - 1, styler))) {
         if (keywordIsAmbiguous(s)
             && keywordIsModifier(s, start, styler)) {
 
@@ -254,7 +254,7 @@ class QuoteCls {
     char Up;
     char Down;
     QuoteCls() {
-        this->New();
+        New();
     }
     void New() {
         Count = 0;
diff --git a/plugins/scintilla/scintilla/lexers/LexSTTXT.cxx b/plugins/scintilla/scintilla/lexers/LexSTTXT.cxx
new file mode 100644
index 0000000..c58d054
--- /dev/null
+++ b/plugins/scintilla/scintilla/lexers/LexSTTXT.cxx
@@ -0,0 +1,401 @@
+// Scintilla source code edit control
+/** @file LexSTTXT.cxx
+ ** Lexer for Structured Text language.
+ ** Written by Pavel Bulochkin
+ **/
+// The License.txt file describes the conditions under which this software may be distributed.
+
+
+#include <stdlib.h>
+#include <string.h>
+#include <stdio.h>
+#include <stdarg.h>
+#include <assert.h>
+#include <ctype.h>
+
+#include "ILexer.h"
+#include "Scintilla.h"
+#include "SciLexer.h"
+
+#include "WordList.h"
+#include "LexAccessor.h"
+#include "Accessor.h"
+#include "StyleContext.h"
+#include "CharacterSet.h"
+#include "LexerModule.h"
+
+#ifdef SCI_NAMESPACE
+using namespace Scintilla;
+#endif
+
+static void ClassifySTTXTWord(WordList *keywordlists[], StyleContext &sc)
+{
+       char s[256] = { 0 };
+       sc.GetCurrentLowered(s, sizeof(s));
+
+       if ((*keywordlists[0]).InList(s)) {
+               sc.ChangeState(SCE_STTXT_KEYWORD);
+       }
+
+       else if ((*keywordlists[1]).InList(s)) {
+               sc.ChangeState(SCE_STTXT_TYPE);
+       }
+
+       else if ((*keywordlists[2]).InList(s)) {
+               sc.ChangeState(SCE_STTXT_FUNCTION);
+       }
+
+       else if ((*keywordlists[3]).InList(s)) {
+               sc.ChangeState(SCE_STTXT_FB);
+       }
+
+       else if ((*keywordlists[4]).InList(s)) {
+               sc.ChangeState(SCE_STTXT_VARS);
+       }
+
+       else if ((*keywordlists[5]).InList(s)) {
+               sc.ChangeState(SCE_STTXT_PRAGMAS);
+       }
+
+       sc.SetState(SCE_STTXT_DEFAULT);
+}
+
+static void ColouriseSTTXTDoc (unsigned int startPos, int length, int initStyle,
+                                                         WordList *keywordlists[], Accessor &styler)
+{
+       StyleContext sc(startPos, length, initStyle, styler);
+
+       CharacterSet setWord(CharacterSet::setAlphaNum, "_", 0x80, true);
+       CharacterSet setWordStart(CharacterSet::setAlpha, "_", 0x80, true);
+       CharacterSet setNumber(CharacterSet::setDigits, "_.eE");
+       CharacterSet setHexNumber(CharacterSet::setDigits, "_abcdefABCDEF");
+       CharacterSet setOperator(CharacterSet::setNone,",.+-*/:;<=>[]()%&");
+       CharacterSet setDataTime(CharacterSet::setDigits,"_.-:dmshDMSH");
+
+       for ( ; sc.More() ; sc.Forward())
+       {
+               if(sc.atLineStart && sc.state != SCE_STTXT_COMMENT)
+                       sc.SetState(SCE_STTXT_DEFAULT);
+
+               switch(sc.state)
+               {
+                       case SCE_STTXT_NUMBER: {
+                               if(!setNumber.Contains(sc.ch))
+                                       sc.SetState(SCE_STTXT_DEFAULT);
+                               break;
+                       }
+                       case SCE_STTXT_HEXNUMBER: {
+                               if(setHexNumber.Contains(sc.ch))
+                                       continue;
+                               else if(setDataTime.Contains(sc.ch))
+                                       sc.SetState(SCE_STTXT_DATETIME);
+                               else
+                                       sc.SetState(SCE_STTXT_DEFAULT);
+
+                               break;
+                       }
+                       case SCE_STTXT_DATETIME: {
+                               if(!setDataTime.Contains(sc.ch))
+                                       sc.SetState(SCE_STTXT_DEFAULT);
+                               break;
+                       }
+                       case SCE_STTXT_OPERATOR: {
+                               sc.SetState(SCE_STTXT_DEFAULT);
+                               break;
+                       }
+                       case SCE_STTXT_PRAGMA: {
+                               if (sc.ch == '}')
+                                       sc.ForwardSetState(SCE_STTXT_DEFAULT);
+                               break;
+                       }
+                       case SCE_STTXT_COMMENTLINE: {
+                               if (sc.atLineStart)
+                                       sc.SetState(SCE_STTXT_DEFAULT);
+                               break;
+                       }
+                       case SCE_STTXT_COMMENT: {
+                               if(sc.Match('*',')'))
+                               {
+                                       sc.Forward();
+                                       sc.ForwardSetState(SCE_STTXT_DEFAULT);
+                               }
+                               break;
+                       }
+                       case SCE_STTXT_STRING1: {
+                               if(sc.atLineEnd)
+                                       sc.SetState(SCE_STTXT_STRINGEOL);
+                               else if(sc.ch == '\'' && sc.chPrev != '$')
+                                       sc.ForwardSetState(SCE_STTXT_DEFAULT);
+                               break;
+                       }
+                       case SCE_STTXT_STRING2: {
+                               if (sc.atLineEnd)
+                                       sc.SetState(SCE_STTXT_STRINGEOL);
+                               else if(sc.ch == '\"' && sc.chPrev != '$')
+                                       sc.ForwardSetState(SCE_STTXT_DEFAULT);
+                               break;
+                       }
+                       case SCE_STTXT_STRINGEOL: {
+                               if(sc.atLineStart)
+                                       sc.SetState(SCE_STTXT_DEFAULT);
+                               break;
+                       }
+                       case SCE_STTXT_CHARACTER: {
+                               if(setHexNumber.Contains(sc.ch))
+                                       sc.SetState(SCE_STTXT_HEXNUMBER);
+                               else if(setDataTime.Contains(sc.ch))
+                                       sc.SetState(SCE_STTXT_DATETIME);
+                               else sc.SetState(SCE_STTXT_DEFAULT);
+                               break;
+                       }
+                       case SCE_STTXT_IDENTIFIER: {
+                               if(!setWord.Contains(sc.ch))
+                                       ClassifySTTXTWord(keywordlists, sc);
+                               break;
+                       }
+               }
+
+               if(sc.state == SCE_STTXT_DEFAULT)
+               {
+                       if(IsADigit(sc.ch))
+                               sc.SetState(SCE_STTXT_NUMBER);
+                       else if (setWordStart.Contains(sc.ch))
+                               sc.SetState(SCE_STTXT_IDENTIFIER);
+                       else if (sc.Match('/', '/'))
+                               sc.SetState(SCE_STTXT_COMMENTLINE);
+                       else if(sc.Match('(', '*'))
+                               sc.SetState(SCE_STTXT_COMMENT);
+                       else if (sc.ch == '{')
+                               sc.SetState(SCE_STTXT_PRAGMA);
+                       else if (sc.ch == '\'')
+                               sc.SetState(SCE_STTXT_STRING1);
+                       else if (sc.ch == '\"')
+                               sc.SetState(SCE_STTXT_STRING2);
+                       else if(sc.ch == '#')
+                               sc.SetState(SCE_STTXT_CHARACTER);
+                       else if (setOperator.Contains(sc.ch))
+                               sc.SetState(SCE_STTXT_OPERATOR);
+               }
+       }
+
+       if (sc.state == SCE_STTXT_IDENTIFIER && setWord.Contains(sc.chPrev))
+               ClassifySTTXTWord(keywordlists, sc);
+
+       sc.Complete();
+}
+
+static const char * const STTXTWordListDesc[] = {
+       "Keywords",
+       "Types",
+       "Functions",
+       "FB",
+       "Local_Var",
+       "Local_Pragma",
+       0
+};
+
+static bool IsCommentLine(int line, Accessor &styler, bool type)
+{
+       int pos = styler.LineStart(line);
+       int eolPos = styler.LineStart(line + 1) - 1;
+
+       for (int i = pos; i < eolPos; i++)
+       {
+               char ch = styler[i];
+               char chNext = styler.SafeGetCharAt(i + 1);
+               int style = styler.StyleAt(i);
+
+               if(type) {
+                        if (ch == '/' && chNext == '/' && style == SCE_STTXT_COMMENTLINE)
+                               return true;
+               }
+               else if (ch == '(' && chNext == '*' && style == SCE_STTXT_COMMENT)
+                       break;
+
+               if (!IsASpaceOrTab(ch))
+                       return false;
+       }
+
+       for (int i = eolPos-2; i>pos; i--)
+       {
+               char ch = styler[i];
+               char chPrev = styler.SafeGetCharAt(i-1);
+               int style = styler.StyleAt(i);
+
+               if(ch == ')' && chPrev == '*' && style == SCE_STTXT_COMMENT)
+                       return true;
+               if(!IsASpaceOrTab(ch))
+                       return false;
+       }
+
+       return false;
+}
+
+static bool IsPragmaLine(int line, Accessor &styler)
+{
+       int pos = styler.LineStart(line);
+       int eolPos = styler.LineStart(line+1) - 1;
+
+       for (int i = pos ; i < eolPos ; i++)
+       {
+               char ch = styler[i];
+               int style = styler.StyleAt(i);
+
+               if(ch == '{' && style == SCE_STTXT_PRAGMA)
+                       return true;
+               else if (!IsASpaceOrTab(ch))
+                       return false;
+       }
+       return false;
+}
+
+static void GetRangeUpper(unsigned int start,unsigned int end,Accessor &styler,char *s,unsigned int len)
+{
+       unsigned int i = 0;
+       while ((i < end - start + 1) && (i < len-1)) {
+               s[i] = static_cast<char>(toupper(styler[start + i]));
+               i++;
+       }
+       s[i] = '\0';
+}
+
+static void ClassifySTTXTWordFoldPoint(int &levelCurrent,unsigned int lastStart,
+                                                                        unsigned int currentPos, Accessor 
&styler)
+{
+       char s[256];
+       GetRangeUpper(lastStart, currentPos, styler, s, sizeof(s));
+
+       // See Table C.2 - Keywords
+       if (!strcmp(s, "ACTION") ||
+               !strcmp(s, "CASE") ||
+               !strcmp(s, "CONFIGURATION") ||
+               !strcmp(s, "FOR") ||
+               !strcmp(s, "FUNCTION") ||
+               !strcmp(s, "FUNCTION_BLOCK") ||
+               !strcmp(s, "IF") ||
+               !strcmp(s, "INITIAL_STEP") ||
+               !strcmp(s, "REPEAT") ||
+               !strcmp(s, "RESOURCE") ||
+               !strcmp(s, "STEP") ||
+               !strcmp(s, "STRUCT") ||
+               !strcmp(s, "TRANSITION") ||
+               !strcmp(s, "TYPE") ||
+               !strcmp(s, "VAR") ||
+               !strcmp(s, "VAR_INPUT") ||
+               !strcmp(s, "VAR_OUTPUT") ||
+               !strcmp(s, "VAR_IN_OUT") ||
+               !strcmp(s, "VAR_TEMP") ||
+               !strcmp(s, "VAR_EXTERNAL") ||
+               !strcmp(s, "VAR_ACCESS") ||
+               !strcmp(s, "VAR_CONFIG") ||
+               !strcmp(s, "VAR_GLOBAL") ||
+               !strcmp(s, "WHILE"))
+       {
+               levelCurrent++;
+       }
+       else if (!strcmp(s, "END_ACTION") ||
+               !strcmp(s, "END_CASE") ||
+               !strcmp(s, "END_CONFIGURATION") ||
+               !strcmp(s, "END_FOR") ||
+               !strcmp(s, "END_FUNCTION") ||
+               !strcmp(s, "END_FUNCTION_BLOCK") ||
+               !strcmp(s, "END_IF") ||
+               !strcmp(s, "END_REPEAT") ||
+               !strcmp(s, "END_RESOURCE") ||
+               !strcmp(s, "END_STEP") ||
+               !strcmp(s, "END_STRUCT") ||
+               !strcmp(s, "END_TRANSITION") ||
+               !strcmp(s, "END_TYPE") ||
+               !strcmp(s, "END_VAR") ||
+               !strcmp(s, "END_WHILE"))
+       {
+               levelCurrent--;
+               if (levelCurrent < SC_FOLDLEVELBASE) {
+                       levelCurrent = SC_FOLDLEVELBASE;
+               }
+       }
+}
+
+static void FoldSTTXTDoc(unsigned int startPos, int length, int initStyle, WordList *[],Accessor &styler)
+{
+       bool foldComment = styler.GetPropertyInt("fold.comment") != 0;
+       bool foldPreprocessor = styler.GetPropertyInt("fold.preprocessor") != 0;
+       bool foldCompact = styler.GetPropertyInt("fold.compact", 1) != 0;
+       unsigned int endPos = startPos + length;
+       int visibleChars = 0;
+       int lineCurrent = styler.GetLine(startPos);
+       int levelPrev = styler.LevelAt(lineCurrent) & SC_FOLDLEVELNUMBERMASK;
+       int levelCurrent = levelPrev;
+       char chNext = styler[startPos];
+       int styleNext = styler.StyleAt(startPos);
+       int style = initStyle;
+       int lastStart = 0;
+
+       CharacterSet setWord(CharacterSet::setAlphaNum, "_", 0x80, true);
+
+       for (unsigned int i = startPos; i < endPos; i++)
+       {
+               char ch = chNext;
+               chNext = styler.SafeGetCharAt(i + 1);
+               int stylePrev = style;
+               style = styleNext;
+               styleNext = styler.StyleAt(i + 1);
+               bool atEOL = (ch == '\r' && chNext != '\n') || (ch == '\n');
+
+               if (foldComment && style == SCE_STTXT_COMMENT) {
+                       if(stylePrev != SCE_STTXT_COMMENT)
+                               levelCurrent++;
+                       else if(styleNext != SCE_STTXT_COMMENT && !atEOL)
+                               levelCurrent--;
+               }
+               if ( foldComment && atEOL && ( IsCommentLine(lineCurrent, styler,false)
+                       || IsCommentLine(lineCurrent,styler,true))) {
+                       if(!IsCommentLine(lineCurrent-1, styler,true) && IsCommentLine(lineCurrent+1, 
styler,true))
+                               levelCurrent++;
+                       if (IsCommentLine(lineCurrent-1, styler,true) && !IsCommentLine(lineCurrent+1, 
styler,true))
+                               levelCurrent--;
+                       if (!IsCommentLine(lineCurrent-1, styler,false) && IsCommentLine(lineCurrent+1, 
styler,false))
+                               levelCurrent++;
+                       if (IsCommentLine(lineCurrent-1, styler,false) && !IsCommentLine(lineCurrent+1, 
styler,false))
+                               levelCurrent--;
+               }
+               if(foldPreprocessor && atEOL && IsPragmaLine(lineCurrent, styler)) {
+                       if(!IsPragmaLine(lineCurrent-1, styler) && IsPragmaLine(lineCurrent+1, styler ))
+                               levelCurrent++;
+                       else if(IsPragmaLine(lineCurrent-1, styler) && !IsPragmaLine(lineCurrent+1, styler))
+                               levelCurrent--;
+               }
+               if (stylePrev != SCE_STTXT_KEYWORD && style == SCE_STTXT_KEYWORD) {
+                               lastStart = i;
+               }
+               if(stylePrev == SCE_STTXT_KEYWORD) {
+                       if(setWord.Contains(ch) && !setWord.Contains(chNext))
+                               ClassifySTTXTWordFoldPoint(levelCurrent,lastStart, i, styler);
+               }
+               if (!IsASpace(ch)) {
+                       visibleChars++;
+               }
+               if (atEOL) {
+                       int lev = levelPrev;
+                       if (visibleChars == 0 && foldCompact)
+                               lev |= SC_FOLDLEVELWHITEFLAG;
+                       if ((levelCurrent > levelPrev) && (visibleChars > 0))
+                               lev |= SC_FOLDLEVELHEADERFLAG;
+                       if (lev != styler.LevelAt(lineCurrent))
+                               styler.SetLevel(lineCurrent, lev);
+
+                       lineCurrent++;
+                       levelPrev = levelCurrent;
+                       visibleChars = 0;
+               }
+
+               // If we didn't reach the EOL in previous loop, store line level and whitespace information.
+               // The rest will be filled in later...
+               int lev = levelPrev;
+               if (visibleChars == 0 && foldCompact)
+                       lev |= SC_FOLDLEVELWHITEFLAG;
+               styler.SetLevel(lineCurrent, lev);
+       }
+}
+
+LexerModule lmSTTXT(SCLEX_STTXT, ColouriseSTTXTDoc, "fcST", FoldSTTXTDoc, STTXTWordListDesc);
diff --git a/plugins/scintilla/scintilla/lexlib/Accessor.cxx b/plugins/scintilla/scintilla/lexlib/Accessor.cxx
index 6560959..f67737d 100644
--- a/plugins/scintilla/scintilla/lexlib/Accessor.cxx
+++ b/plugins/scintilla/scintilla/lexlib/Accessor.cxx
@@ -28,7 +28,7 @@ using namespace Scintilla;
 Accessor::Accessor(IDocument *pAccess_, PropSetSimple *pprops_) : LexAccessor(pAccess_), pprops(pprops_) {
 }
 
-int Accessor::GetPropertyInt(const char *key, int defaultValue) {
+int Accessor::GetPropertyInt(const char *key, int defaultValue) const {
        return pprops->GetInt(key, defaultValue);
 }
 
diff --git a/plugins/scintilla/scintilla/lexlib/Accessor.h b/plugins/scintilla/scintilla/lexlib/Accessor.h
index 2f28c1a..9789f2b 100644
--- a/plugins/scintilla/scintilla/lexlib/Accessor.h
+++ b/plugins/scintilla/scintilla/lexlib/Accessor.h
@@ -24,7 +24,7 @@ class Accessor : public LexAccessor {
 public:
        PropSetSimple *pprops;
        Accessor(IDocument *pAccess_, PropSetSimple *pprops_);
-       int GetPropertyInt(const char *, int defaultValue=0);
+       int GetPropertyInt(const char *, int defaultValue=0) const;
        int IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader = 0);
 };
 
diff --git a/plugins/scintilla/scintilla/lexlib/CharacterCategory.cxx 
b/plugins/scintilla/scintilla/lexlib/CharacterCategory.cxx
new file mode 100644
index 0000000..a837760
--- /dev/null
+++ b/plugins/scintilla/scintilla/lexlib/CharacterCategory.cxx
@@ -0,0 +1,3303 @@
+// Scintilla source code edit control
+/** @file CharacterCategory.cxx
+ ** Returns the Unicode general category of a character.
+ ** Table automatically regenerated by scripts/GenerateCharacterCategory.py
+ ** Should only be rarely regenerated for new versions of Unicode.
+ **/
+// Copyright 2013 by Neil Hodgson <neilh scintilla org>
+// The License.txt file describes the conditions under which this software may be distributed.
+
+#include <algorithm>
+
+#include "CharacterCategory.h"
+
+#ifdef SCI_NAMESPACE
+namespace Scintilla {
+#endif
+
+namespace {
+       // Use an unnamed namespace to protect the declarations from name conflicts
+
+const int catRanges[] = {
+//++Autogenerated -- start of section automatically generated
+// Created with Python 3.3.0,  Unicode 6.1.0
+25,
+1046,
+1073,
+1171,
+1201,
+1293,
+1326,
+1361,
+1394,
+1425,
+1452,
+1489,
+1544,
+1873,
+1938,
+2033,
+2080,
+2925,
+2961,
+2990,
+3028,
+3051,
+3092,
+3105,
+3949,
+3986,
+4014,
+4050,
+4089,
+5142,
+5169,
+5203,
+5333,
+5361,
+5396,
+5429,
+5444,
+5487,
+5522,
+5562,
+5589,
+5620,
+5653,
+5682,
+5706,
+5780,
+5793,
+5841,
+5908,
+5930,
+5956,
+6000,
+6026,
+6129,
+6144,
+6898,
+6912,
+7137,
+7922,
+7937,
+8192,
+8225,
+8256,
+8289,
+8320,
+8353,
+8384,
+8417,
+8448,
+8481,
+8512,
+8545,
+8576,
+8609,
+8640,
+8673,
+8704,
+8737,
+8768,
+8801,
+8832,
+8865,
+8896,
+8929,
+8960,
+8993,
+9024,
+9057,
+9088,
+9121,
+9152,
+9185,
+9216,
+9249,
+9280,
+9313,
+9344,
+9377,
+9408,
+9441,
+9472,
+9505,
+9536,
+9569,
+9600,
+9633,
+9664,
+9697,
+9728,
+9761,
+9792,
+9825,
+9856,
+9889,
+9920,
+9953,
+10016,
+10049,
+10080,
+10113,
+10144,
+10177,
+10208,
+10241,
+10272,
+10305,
+10336,
+10369,
+10400,
+10433,
+10464,
+10497,
+10560,
+10593,
+10624,
+10657,
+10688,
+10721,
+10752,
+10785,
+10816,
+10849,
+10880,
+10913,
+10944,
+10977,
+11008,
+11041,
+11072,
+11105,
+11136,
+11169,
+11200,
+11233,
+11264,
+11297,
+11328,
+11361,
+11392,
+11425,
+11456,
+11489,
+11520,
+11553,
+11584,
+11617,
+11648,
+11681,
+11712,
+11745,
+11776,
+11809,
+11840,
+11873,
+11904,
+11937,
+11968,
+12001,
+12032,
+12097,
+12128,
+12161,
+12192,
+12225,
+12320,
+12385,
+12416,
+12449,
+12480,
+12545,
+12576,
+12673,
+12736,
+12865,
+12896,
+12961,
+12992,
+13089,
+13184,
+13249,
+13280,
+13345,
+13376,
+13409,
+13440,
+13473,
+13504,
+13569,
+13600,
+13633,
+13696,
+13729,
+13760,
+13825,
+13856,
+13953,
+13984,
+14017,
+14048,
+14113,
+14180,
+14208,
+14241,
+14340,
+14464,
+14498,
+14529,
+14560,
+14594,
+14625,
+14656,
+14690,
+14721,
+14752,
+14785,
+14816,
+14849,
+14880,
+14913,
+14944,
+14977,
+15008,
+15041,
+15072,
+15105,
+15136,
+15169,
+15200,
+15233,
+15296,
+15329,
+15360,
+15393,
+15424,
+15457,
+15488,
+15521,
+15552,
+15585,
+15616,
+15649,
+15680,
+15713,
+15744,
+15777,
+15808,
+15841,
+15904,
+15938,
+15969,
+16000,
+16033,
+16064,
+16161,
+16192,
+16225,
+16256,
+16289,
+16320,
+16353,
+16384,
+16417,
+16448,
+16481,
+16512,
+16545,
+16576,
+16609,
+16640,
+16673,
+16704,
+16737,
+16768,
+16801,
+16832,
+16865,
+16896,
+16929,
+16960,
+16993,
+17024,
+17057,
+17088,
+17121,
+17152,
+17185,
+17216,
+17249,
+17280,
+17313,
+17344,
+17377,
+17408,
+17441,
+17472,
+17505,
+17536,
+17569,
+17600,
+17633,
+17664,
+17697,
+17728,
+17761,
+17792,
+17825,
+17856,
+17889,
+17920,
+17953,
+17984,
+18017,
+18240,
+18305,
+18336,
+18401,
+18464,
+18497,
+18528,
+18657,
+18688,
+18721,
+18752,
+18785,
+18816,
+18849,
+18880,
+18913,
+21124,
+21153,
+22019,
+22612,
+22723,
+23124,
+23555,
+23732,
+23939,
+23988,
+24003,
+24052,
+24581,
+28160,
+28193,
+28224,
+28257,
+28291,
+28340,
+28352,
+28385,
+28445,
+28483,
+28513,
+28625,
+28669,
+28820,
+28864,
+28913,
+28928,
+29053,
+29056,
+29117,
+29120,
+29185,
+29216,
+29789,
+29792,
+30081,
+31200,
+31233,
+31296,
+31393,
+31488,
+31521,
+31552,
+31585,
+31616,
+31649,
+31680,
+31713,
+31744,
+31777,
+31808,
+31841,
+31872,
+31905,
+31936,
+31969,
+32000,
+32033,
+32064,
+32097,
+32128,
+32161,
+32192,
+32225,
+32384,
+32417,
+32466,
+32480,
+32513,
+32544,
+32609,
+32672,
+34305,
+35840,
+35873,
+35904,
+35937,
+35968,
+36001,
+36032,
+36065,
+36096,
+36129,
+36160,
+36193,
+36224,
+36257,
+36288,
+36321,
+36352,
+36385,
+36416,
+36449,
+36480,
+36513,
+36544,
+36577,
+36608,
+36641,
+36672,
+36705,
+36736,
+36769,
+36800,
+36833,
+36864,
+36897,
+36949,
+36965,
+37127,
+37184,
+37217,
+37248,
+37281,
+37312,
+37345,
+37376,
+37409,
+37440,
+37473,
+37504,
+37537,
+37568,
+37601,
+37632,
+37665,
+37696,
+37729,
+37760,
+37793,
+37824,
+37857,
+37888,
+37921,
+37952,
+37985,
+38016,
+38049,
+38080,
+38113,
+38144,
+38177,
+38208,
+38241,
+38272,
+38305,
+38336,
+38369,
+38400,
+38433,
+38464,
+38497,
+38528,
+38561,
+38592,
+38625,
+38656,
+38689,
+38720,
+38753,
+38784,
+38817,
+38848,
+38881,
+38912,
+38977,
+39008,
+39041,
+39072,
+39105,
+39136,
+39169,
+39200,
+39233,
+39264,
+39297,
+39328,
+39361,
+39424,
+39457,
+39488,
+39521,
+39552,
+39585,
+39616,
+39649,
+39680,
+39713,
+39744,
+39777,
+39808,
+39841,
+39872,
+39905,
+39936,
+39969,
+40000,
+40033,
+40064,
+40097,
+40128,
+40161,
+40192,
+40225,
+40256,
+40289,
+40320,
+40353,
+40384,
+40417,
+40448,
+40481,
+40512,
+40545,
+40576,
+40609,
+40640,
+40673,
+40704,
+40737,
+40768,
+40801,
+40832,
+40865,
+40896,
+40929,
+40960,
+40993,
+41024,
+41057,
+41088,
+41121,
+41152,
+41185,
+41216,
+41249,
+41280,
+41313,
+41344,
+41377,
+41408,
+41441,
+41472,
+41505,
+41536,
+41569,
+41600,
+41633,
+41664,
+41697,
+41728,
+41761,
+41792,
+41825,
+41856,
+41889,
+41920,
+41953,
+41984,
+42017,
+42048,
+42081,
+42112,
+42145,
+42176,
+42209,
+42269,
+42528,
+43773,
+43811,
+43857,
+44061,
+44065,
+45341,
+45361,
+45388,
+45437,
+45555,
+45597,
+45605,
+47052,
+47077,
+47121,
+47141,
+47217,
+47237,
+47313,
+47333,
+47389,
+47620,
+48509,
+48644,
+48753,
+48829,
+49178,
+49341,
+49362,
+49457,
+49523,
+49553,
+49621,
+49669,
+50033,
+50077,
+50129,
+50180,
+51203,
+51236,
+51557,
+52232,
+52561,
+52676,
+52741,
+52772,
+55953,
+55972,
+56005,
+56250,
+56277,
+56293,
+56483,
+56549,
+56629,
+56645,
+56772,
+56840,
+57156,
+57269,
+57316,
+57361,
+57821,
+57850,
+57860,
+57893,
+57924,
+58885,
+59773,
+59812,
+62661,
+63012,
+63069,
+63496,
+63812,
+64869,
+65155,
+65237,
+65265,
+65347,
+65405,
+65540,
+66245,
+66371,
+66405,
+66691,
+66725,
+66819,
+66853,
+67037,
+67089,
+67581,
+67588,
+68389,
+68509,
+68561,
+68605,
+70660,
+70717,
+70724,
+71101,
+72837,
+73725,
+73733,
+73830,
+73860,
+75589,
+75622,
+75653,
+75684,
+75718,
+75813,
+76070,
+76197,
+76230,
+76292,
+76325,
+76548,
+76869,
+76945,
+77000,
+77329,
+77347,
+77380,
+77597,
+77604,
+77853,
+77861,
+77894,
+77981,
+77988,
+78269,
+78308,
+78397,
+78436,
+79165,
+79172,
+79421,
+79428,
+79485,
+79556,
+79709,
+79749,
+79780,
+79814,
+79909,
+80061,
+80102,
+80189,
+80230,
+80293,
+80324,
+80381,
+80614,
+80669,
+80772,
+80861,
+80868,
+80965,
+81053,
+81096,
+81412,
+81491,
+81546,
+81749,
+81779,
+81821,
+81957,
+82022,
+82077,
+82084,
+82301,
+82404,
+82493,
+82532,
+83261,
+83268,
+83517,
+83524,
+83613,
+83620,
+83709,
+83716,
+83805,
+83845,
+83901,
+83910,
+84005,
+84093,
+84197,
+84285,
+84325,
+84445,
+84517,
+84573,
+84772,
+84925,
+84932,
+84989,
+85192,
+85509,
+85572,
+85669,
+85725,
+86053,
+86118,
+86173,
+86180,
+86493,
+86500,
+86621,
+86628,
+87357,
+87364,
+87613,
+87620,
+87709,
+87716,
+87901,
+87941,
+87972,
+88006,
+88101,
+88285,
+88293,
+88358,
+88413,
+88422,
+88485,
+88541,
+88580,
+88637,
+89092,
+89157,
+89245,
+89288,
+89617,
+89651,
+89693,
+90149,
+90182,
+90269,
+90276,
+90557,
+90596,
+90685,
+90724,
+91453,
+91460,
+91709,
+91716,
+91805,
+91812,
+91997,
+92037,
+92068,
+92102,
+92133,
+92166,
+92197,
+92349,
+92390,
+92477,
+92518,
+92581,
+92637,
+92869,
+92902,
+92957,
+93060,
+93149,
+93156,
+93253,
+93341,
+93384,
+93717,
+93732,
+93770,
+93981,
+94277,
+94308,
+94365,
+94372,
+94589,
+94660,
+94781,
+94788,
+94941,
+95012,
+95101,
+95108,
+95165,
+95172,
+95261,
+95332,
+95421,
+95492,
+95613,
+95684,
+96093,
+96198,
+96261,
+96294,
+96381,
+96454,
+96573,
+96582,
+96677,
+96733,
+96772,
+96829,
+96998,
+97053,
+97480,
+97802,
+97909,
+98099,
+98133,
+98173,
+98342,
+98461,
+98468,
+98749,
+98756,
+98877,
+98884,
+99645,
+99652,
+99997,
+100004,
+100189,
+100260,
+100293,
+100390,
+100541,
+100549,
+100669,
+100677,
+100829,
+101029,
+101117,
+101124,
+101213,
+101380,
+101445,
+101533,
+101576,
+101917,
+102154,
+102389,
+102429,
+102470,
+102557,
+102564,
+102845,
+102852,
+102973,
+102980,
+103741,
+103748,
+104093,
+104100,
+104285,
+104325,
+104356,
+104390,
+104421,
+104454,
+104637,
+104645,
+104678,
+104765,
+104774,
+104837,
+104925,
+105126,
+105213,
+105412,
+105469,
+105476,
+105541,
+105629,
+105672,
+106013,
+106020,
+106109,
+106566,
+106653,
+106660,
+106941,
+106948,
+107069,
+107076,
+108413,
+108452,
+108486,
+108581,
+108733,
+108742,
+108861,
+108870,
+108965,
+108996,
+109053,
+109286,
+109341,
+109572,
+109637,
+109725,
+109768,
+110090,
+110301,
+110389,
+110404,
+110621,
+110662,
+110749,
+110756,
+111357,
+111428,
+112221,
+112228,
+112541,
+112548,
+112605,
+112644,
+112893,
+112965,
+113021,
+113126,
+113221,
+113341,
+113349,
+113405,
+113414,
+113693,
+114246,
+114321,
+114365,
+114724,
+116261,
+116292,
+116357,
+116605,
+116723,
+116740,
+116931,
+116965,
+117233,
+117256,
+117585,
+117661,
+118820,
+118909,
+118916,
+118973,
+119012,
+119101,
+119108,
+119165,
+119204,
+119261,
+119428,
+119581,
+119588,
+119837,
+119844,
+119965,
+119972,
+120029,
+120036,
+120093,
+120132,
+120221,
+120228,
+120357,
+120388,
+120453,
+120669,
+120677,
+120740,
+120797,
+120836,
+121021,
+121027,
+121085,
+121093,
+121309,
+121352,
+121693,
+121732,
+121885,
+122884,
+122933,
+123025,
+123509,
+123537,
+123573,
+123653,
+123733,
+123912,
+124234,
+124565,
+124581,
+124629,
+124645,
+124693,
+124709,
+124749,
+124782,
+124813,
+124846,
+124870,
+124932,
+125213,
+125220,
+126397,
+126501,
+126950,
+126981,
+127153,
+127173,
+127236,
+127397,
+127773,
+127781,
+128957,
+128981,
+129221,
+129269,
+129469,
+129493,
+129553,
+129717,
+129841,
+129917,
+131076,
+132454,
+132517,
+132646,
+132677,
+132870,
+132901,
+132966,
+133029,
+133092,
+133128,
+133457,
+133636,
+133830,
+133893,
+133956,
+134085,
+134180,
+134214,
+134308,
+134374,
+134596,
+134693,
+134820,
+135237,
+135270,
+135333,
+135398,
+135589,
+135620,
+135654,
+135688,
+136006,
+136101,
+136149,
+136192,
+137437,
+137440,
+137501,
+137632,
+137693,
+137732,
+139121,
+139139,
+139172,
+149821,
+149828,
+149981,
+150020,
+150269,
+150276,
+150333,
+150340,
+150493,
+150532,
+151869,
+151876,
+152029,
+152068,
+153149,
+153156,
+153309,
+153348,
+153597,
+153604,
+153661,
+153668,
+153821,
+153860,
+154365,
+154372,
+156221,
+156228,
+156381,
+156420,
+158589,
+158629,
+158737,
+159018,
+159677,
+159748,
+160277,
+160605,
+160772,
+163517,
+163852,
+163876,
+183729,
+183780,
+184342,
+184356,
+185197,
+185230,
+185277,
+185348,
+187761,
+187849,
+187965,
+188420,
+188861,
+188868,
+188997,
+189117,
+189444,
+190021,
+190129,
+190205,
+190468,
+191045,
+191133,
+191492,
+191933,
+191940,
+192061,
+192069,
+192157,
+192516,
+194181,
+194246,
+194277,
+194502,
+194757,
+194790,
+194853,
+195217,
+195299,
+195345,
+195443,
+195460,
+195493,
+195549,
+195592,
+195933,
+196106,
+196445,
+196625,
+196812,
+196849,
+196965,
+197078,
+197117,
+197128,
+197469,
+197636,
+198755,
+198788,
+200477,
+200708,
+202021,
+202052,
+202109,
+202244,
+204509,
+204804,
+205757,
+205829,
+205926,
+206053,
+206118,
+206237,
+206342,
+206405,
+206438,
+206629,
+206749,
+206869,
+206909,
+206993,
+207048,
+207364,
+208349,
+208388,
+208573,
+208900,
+210333,
+210438,
+210980,
+211206,
+211293,
+211464,
+211786,
+211837,
+211925,
+212996,
+213733,
+213798,
+213917,
+213969,
+214020,
+215718,
+215749,
+215782,
+215813,
+216061,
+216069,
+216102,
+216133,
+216166,
+216229,
+216486,
+216677,
+217021,
+217061,
+217096,
+217437,
+217608,
+217949,
+218129,
+218339,
+218385,
+218589,
+221189,
+221318,
+221348,
+222853,
+222886,
+222917,
+223078,
+223109,
+223142,
+223301,
+223334,
+223396,
+223645,
+223752,
+224081,
+224309,
+224613,
+224917,
+225213,
+225285,
+225350,
+225380,
+226342,
+226373,
+226502,
+226565,
+226630,
+226661,
+226694,
+226756,
+226824,
+227140,
+228549,
+228582,
+228613,
+228678,
+228773,
+228806,
+228837,
+228934,
+229021,
+229265,
+229380,
+230534,
+230789,
+231046,
+231109,
+231197,
+231281,
+231432,
+231773,
+231844,
+231944,
+232260,
+233219,
+233425,
+233501,
+235537,
+235805,
+236037,
+236145,
+236165,
+236582,
+236613,
+236836,
+236965,
+236996,
+237126,
+237189,
+237220,
+237309,
+237569,
+238979,
+240993,
+241411,
+241441,
+242531,
+243717,
+244989,
+245637,
+245760,
+245793,
+245824,
+245857,
+245888,
+245921,
+245952,
+245985,
+246016,
+246049,
+246080,
+246113,
+246144,
+246177,
+246208,
+246241,
+246272,
+246305,
+246336,
+246369,
+246400,
+246433,
+246464,
+246497,
+246528,
+246561,
+246592,
+246625,
+246656,
+246689,
+246720,
+246753,
+246784,
+246817,
+246848,
+246881,
+246912,
+246945,
+246976,
+247009,
+247040,
+247073,
+247104,
+247137,
+247168,
+247201,
+247232,
+247265,
+247296,
+247329,
+247360,
+247393,
+247424,
+247457,
+247488,
+247521,
+247552,
+247585,
+247616,
+247649,
+247680,
+247713,
+247744,
+247777,
+247808,
+247841,
+247872,
+247905,
+247936,
+247969,
+248000,
+248033,
+248064,
+248097,
+248128,
+248161,
+248192,
+248225,
+248256,
+248289,
+248320,
+248353,
+248384,
+248417,
+248448,
+248481,
+248512,
+248545,
+248576,
+248609,
+248640,
+248673,
+248704,
+248737,
+248768,
+248801,
+248832,
+248865,
+248896,
+248929,
+248960,
+248993,
+249024,
+249057,
+249088,
+249121,
+249152,
+249185,
+249216,
+249249,
+249280,
+249313,
+249344,
+249377,
+249408,
+249441,
+249472,
+249505,
+249536,
+249569,
+249600,
+249633,
+249664,
+249697,
+249728,
+249761,
+249792,
+249825,
+249856,
+249889,
+249920,
+249953,
+249984,
+250017,
+250048,
+250081,
+250112,
+250145,
+250176,
+250209,
+250240,
+250273,
+250304,
+250337,
+250368,
+250401,
+250432,
+250465,
+250496,
+250529,
+250816,
+250849,
+250880,
+250913,
+250944,
+250977,
+251008,
+251041,
+251072,
+251105,
+251136,
+251169,
+251200,
+251233,
+251264,
+251297,
+251328,
+251361,
+251392,
+251425,
+251456,
+251489,
+251520,
+251553,
+251584,
+251617,
+251648,
+251681,
+251712,
+251745,
+251776,
+251809,
+251840,
+251873,
+251904,
+251937,
+251968,
+252001,
+252032,
+252065,
+252096,
+252129,
+252160,
+252193,
+252224,
+252257,
+252288,
+252321,
+252352,
+252385,
+252416,
+252449,
+252480,
+252513,
+252544,
+252577,
+252608,
+252641,
+252672,
+252705,
+252736,
+252769,
+252800,
+252833,
+252864,
+252897,
+252928,
+252961,
+252992,
+253025,
+253056,
+253089,
+253120,
+253153,
+253184,
+253217,
+253248,
+253281,
+253312,
+253345,
+253376,
+253409,
+253440,
+253473,
+253504,
+253537,
+253568,
+253601,
+253632,
+253665,
+253696,
+253729,
+253760,
+253793,
+253824,
+253857,
+253888,
+253921,
+254208,
+254465,
+254685,
+254720,
+254941,
+254977,
+255232,
+255489,
+255744,
+256001,
+256221,
+256256,
+256477,
+256513,
+256797,
+256800,
+256861,
+256864,
+256925,
+256928,
+256989,
+256992,
+257025,
+257280,
+257537,
+258013,
+258049,
+258306,
+258561,
+258818,
+259073,
+259330,
+259585,
+259773,
+259777,
+259840,
+259970,
+260020,
+260033,
+260084,
+260161,
+260285,
+260289,
+260352,
+260482,
+260532,
+260609,
+260765,
+260801,
+260864,
+261021,
+261044,
+261121,
+261376,
+261556,
+261661,
+261697,
+261821,
+261825,
+261888,
+262018,
+262068,
+262141,
+262166,
+262522,
+262668,
+262865,
+262927,
+262960,
+262989,
+263023,
+263088,
+263117,
+263151,
+263185,
+263447,
+263480,
+263514,
+263670,
+263697,
+263983,
+264016,
+264049,
+264171,
+264241,
+264338,
+264365,
+264398,
+264433,
+264786,
+264817,
+264843,
+264881,
+265206,
+265242,
+265405,
+265562,
+265738,
+265763,
+265821,
+265866,
+266066,
+266157,
+266190,
+266211,
+266250,
+266578,
+266669,
+266702,
+266749,
+266755,
+267197,
+267283,
+268125,
+268805,
+269223,
+269349,
+269383,
+269477,
+269885,
+270357,
+270400,
+270453,
+270560,
+270613,
+270657,
+270688,
+270785,
+270848,
+270945,
+270997,
+271008,
+271061,
+271122,
+271136,
+271317,
+271488,
+271541,
+271552,
+271605,
+271616,
+271669,
+271680,
+271829,
+271841,
+271872,
+272001,
+272036,
+272161,
+272213,
+272257,
+272320,
+272402,
+272544,
+272577,
+272725,
+272754,
+272789,
+272833,
+272885,
+272906,
+273417,
+274528,
+274561,
+274601,
+274730,
+274781,
+274962,
+275125,
+275282,
+275349,
+275474,
+275509,
+275570,
+275605,
+275666,
+275701,
+275922,
+275957,
+276946,
+277013,
+277074,
+277109,
+277138,
+277173,
+278162,
+286741,
+286994,
+287125,
+287762,
+287829,
+288045,
+288078,
+288117,
+290706,
+290741,
+291698,
+292501,
+293778,
+293973,
+294557,
+294933,
+296189,
+296981,
+297341,
+297994,
+299925,
+302410,
+303125,
+308978,
+309013,
+309298,
+309333,
+311058,
+311317,
+314866,
+314901,
+319517,
+319541,
+322829,
+322862,
+322893,
+322926,
+322957,
+322990,
+323021,
+323054,
+323085,
+323118,
+323149,
+323182,
+323213,
+323246,
+323274,
+324245,
+325650,
+325805,
+325838,
+325874,
+326861,
+326894,
+326925,
+326958,
+326989,
+327022,
+327053,
+327086,
+327117,
+327150,
+327186,
+327701,
+335890,
+340077,
+340110,
+340141,
+340174,
+340205,
+340238,
+340269,
+340302,
+340333,
+340366,
+340397,
+340430,
+340461,
+340494,
+340525,
+340558,
+340589,
+340622,
+340653,
+340686,
+340717,
+340750,
+340786,
+342797,
+342830,
+342861,
+342894,
+342930,
+343949,
+343982,
+344018,
+352277,
+353810,
+354485,
+354546,
+354749,
+354837,
+355165,
+360448,
+361981,
+361985,
+363517,
+363520,
+363553,
+363584,
+363681,
+363744,
+363777,
+363808,
+363841,
+363872,
+363905,
+363936,
+364065,
+364096,
+364129,
+364192,
+364225,
+364419,
+364480,
+364577,
+364608,
+364641,
+364672,
+364705,
+364736,
+364769,
+364800,
+364833,
+364864,
+364897,
+364928,
+364961,
+364992,
+365025,
+365056,
+365089,
+365120,
+365153,
+365184,
+365217,
+365248,
+365281,
+365312,
+365345,
+365376,
+365409,
+365440,
+365473,
+365504,
+365537,
+365568,
+365601,
+365632,
+365665,
+365696,
+365729,
+365760,
+365793,
+365824,
+365857,
+365888,
+365921,
+365952,
+365985,
+366016,
+366049,
+366080,
+366113,
+366144,
+366177,
+366208,
+366241,
+366272,
+366305,
+366336,
+366369,
+366400,
+366433,
+366464,
+366497,
+366528,
+366561,
+366592,
+366625,
+366656,
+366689,
+366720,
+366753,
+366784,
+366817,
+366848,
+366881,
+366912,
+366945,
+366976,
+367009,
+367040,
+367073,
+367104,
+367137,
+367168,
+367201,
+367232,
+367265,
+367296,
+367329,
+367360,
+367393,
+367424,
+367457,
+367488,
+367521,
+367552,
+367585,
+367616,
+367649,
+367680,
+367713,
+367797,
+367968,
+368001,
+368032,
+368065,
+368101,
+368192,
+368225,
+368285,
+368433,
+368554,
+368593,
+368641,
+369885,
+369889,
+369949,
+370081,
+370141,
+370180,
+371997,
+372195,
+372241,
+372285,
+372709,
+372740,
+373501,
+373764,
+374013,
+374020,
+374269,
+374276,
+374525,
+374532,
+374781,
+374788,
+375037,
+375044,
+375293,
+375300,
+375549,
+375556,
+375805,
+375813,
+376849,
+376911,
+376944,
+376975,
+377008,
+377041,
+377135,
+377168,
+377201,
+377231,
+377264,
+377297,
+377580,
+377617,
+377676,
+377713,
+377743,
+377776,
+377809,
+377871,
+377904,
+377933,
+377966,
+377997,
+378030,
+378061,
+378094,
+378125,
+378158,
+378193,
+378339,
+378385,
+378700,
+378781,
+380949,
+381789,
+381813,
+384669,
+385045,
+391901,
+392725,
+393117,
+393238,
+393265,
+393365,
+393379,
+393412,
+393449,
+393485,
+393518,
+393549,
+393582,
+393613,
+393646,
+393677,
+393710,
+393741,
+393774,
+393813,
+393869,
+393902,
+393933,
+393966,
+393997,
+394030,
+394061,
+394094,
+394124,
+394157,
+394190,
+394261,
+394281,
+394565,
+394694,
+394764,
+394787,
+394965,
+395017,
+395107,
+395140,
+395185,
+395221,
+395293,
+395300,
+398077,
+398117,
+398196,
+398243,
+398308,
+398348,
+398372,
+401265,
+401283,
+401380,
+401437,
+401572,
+402909,
+402980,
+406013,
+406037,
+406090,
+406229,
+406532,
+407421,
+407573,
+408733,
+409092,
+409621,
+410621,
+410634,
+410965,
+411914,
+412181,
+412202,
+412693,
+413706,
+414037,
+415274,
+415765,
+417789,
+417813,
+425988,
+636637,
+636949,
+638980,
+1309117,
+1310724,
+1311395,
+1311428,
+1348029,
+1348117,
+1349885,
+1350148,
+1351427,
+1351633,
+1351684,
+1360259,
+1360305,
+1360388,
+1360904,
+1361220,
+1361309,
+1361920,
+1361953,
+1361984,
+1362017,
+1362048,
+1362081,
+1362112,
+1362145,
+1362176,
+1362209,
+1362240,
+1362273,
+1362304,
+1362337,
+1362368,
+1362401,
+1362432,
+1362465,
+1362496,
+1362529,
+1362560,
+1362593,
+1362624,
+1362657,
+1362688,
+1362721,
+1362752,
+1362785,
+1362816,
+1362849,
+1362880,
+1362913,
+1362944,
+1362977,
+1363008,
+1363041,
+1363072,
+1363105,
+1363136,
+1363169,
+1363200,
+1363233,
+1363264,
+1363297,
+1363328,
+1363361,
+1363396,
+1363429,
+1363463,
+1363569,
+1363589,
+1363921,
+1363939,
+1363968,
+1364001,
+1364032,
+1364065,
+1364096,
+1364129,
+1364160,
+1364193,
+1364224,
+1364257,
+1364288,
+1364321,
+1364352,
+1364385,
+1364416,
+1364449,
+1364480,
+1364513,
+1364544,
+1364577,
+1364608,
+1364641,
+1364672,
+1364705,
+1364765,
+1364965,
+1364996,
+1367241,
+1367557,
+1367633,
+1367837,
+1368084,
+1368803,
+1369108,
+1369152,
+1369185,
+1369216,
+1369249,
+1369280,
+1369313,
+1369344,
+1369377,
+1369408,
+1369441,
+1369472,
+1369505,
+1369536,
+1369569,
+1369664,
+1369697,
+1369728,
+1369761,
+1369792,
+1369825,
+1369856,
+1369889,
+1369920,
+1369953,
+1369984,
+1370017,
+1370048,
+1370081,
+1370112,
+1370145,
+1370176,
+1370209,
+1370240,
+1370273,
+1370304,
+1370337,
+1370368,
+1370401,
+1370432,
+1370465,
+1370496,
+1370529,
+1370560,
+1370593,
+1370624,
+1370657,
+1370688,
+1370721,
+1370752,
+1370785,
+1370816,
+1370849,
+1370880,
+1370913,
+1370944,
+1370977,
+1371008,
+1371041,
+1371072,
+1371105,
+1371136,
+1371169,
+1371200,
+1371233,
+1371264,
+1371297,
+1371328,
+1371361,
+1371392,
+1371425,
+1371456,
+1371489,
+1371520,
+1371553,
+1371584,
+1371617,
+1371651,
+1371681,
+1371936,
+1371969,
+1372000,
+1372033,
+1372064,
+1372129,
+1372160,
+1372193,
+1372224,
+1372257,
+1372288,
+1372321,
+1372352,
+1372385,
+1372419,
+1372468,
+1372512,
+1372545,
+1372576,
+1372609,
+1372669,
+1372672,
+1372705,
+1372736,
+1372769,
+1372829,
+1373184,
+1373217,
+1373248,
+1373281,
+1373312,
+1373345,
+1373376,
+1373409,
+1373440,
+1373473,
+1373504,
+1373565,
+1376003,
+1376065,
+1376100,
+1376325,
+1376356,
+1376453,
+1376484,
+1376613,
+1376644,
+1377382,
+1377445,
+1377510,
+1377557,
+1377693,
+1377802,
+1378005,
+1378067,
+1378101,
+1378141,
+1378308,
+1379985,
+1380125,
+1380358,
+1380420,
+1382022,
+1382533,
+1382589,
+1382865,
+1382920,
+1383261,
+1383429,
+1384004,
+1384209,
+1384292,
+1384349,
+1384456,
+1384772,
+1385669,
+1385937,
+1385988,
+1386725,
+1387078,
+1387165,
+1387505,
+1387524,
+1388477,
+1388549,
+1388646,
+1388676,
+1390181,
+1390214,
+1390277,
+1390406,
+1390469,
+1390502,
+1390641,
+1391069,
+1391075,
+1391112,
+1391453,
+1391569,
+1391645,
+1392644,
+1393957,
+1394150,
+1394213,
+1394278,
+1394341,
+1394429,
+1394692,
+1394789,
+1394820,
+1395077,
+1395110,
+1395165,
+1395208,
+1395549,
+1395601,
+1395716,
+1396227,
+1396260,
+1396469,
+1396548,
+1396582,
+1396637,
+1396740,
+1398277,
+1398308,
+1398341,
+1398436,
+1398501,
+1398564,
+1398725,
+1398788,
+1398821,
+1398852,
+1398909,
+1399652,
+1399715,
+1399761,
+1399812,
+1400166,
+1400197,
+1400262,
+1400337,
+1400388,
+1400419,
+1400486,
+1400517,
+1400573,
+1400868,
+1401085,
+1401124,
+1401341,
+1401380,
+1401597,
+1401860,
+1402109,
+1402116,
+1402365,
+1406980,
+1408102,
+1408165,
+1408198,
+1408261,
+1408294,
+1408369,
+1408390,
+1408421,
+1408477,
+1408520,
+1408861,
+1409028,
+1766557,
+1766916,
+1767677,
+1767780,
+1769373,
+1769499,
+1835036,
+2039812,
+2051549,
+2051588,
+2055005,
+2056193,
+2056445,
+2056801,
+2056989,
+2057124,
+2057157,
+2057188,
+2057522,
+2057540,
+2057981,
+2057988,
+2058173,
+2058180,
+2058237,
+2058244,
+2058333,
+2058340,
+2058429,
+2058436,
+2061908,
+2062429,
+2062948,
+2074573,
+2074606,
+2074653,
+2075140,
+2077213,
+2077252,
+2079005,
+2080260,
+2080659,
+2080693,
+2080733,
+2080773,
+2081297,
+2081517,
+2081550,
+2081585,
+2081629,
+2081797,
+2082045,
+2082321,
+2082348,
+2082411,
+2082477,
+2082510,
+2082541,
+2082574,
+2082605,
+2082638,
+2082669,
+2082702,
+2082733,
+2082766,
+2082797,
+2082830,
+2082861,
+2082894,
+2082925,
+2082958,
+2082993,
+2083053,
+2083086,
+2083121,
+2083243,
+2083345,
+2083453,
+2083473,
+2083596,
+2083629,
+2083662,
+2083693,
+2083726,
+2083757,
+2083790,
+2083825,
+2083922,
+2083948,
+2083986,
+2084093,
+2084113,
+2084147,
+2084177,
+2084253,
+2084356,
+2084541,
+2084548,
+2088893,
+2088954,
+2088989,
+2089009,
+2089107,
+2089137,
+2089229,
+2089262,
+2089297,
+2089330,
+2089361,
+2089388,
+2089425,
+2089480,
+2089809,
+2089874,
+2089969,
+2090016,
+2090861,
+2090897,
+2090926,
+2090964,
+2090987,
+2091028,
+2091041,
+2091885,
+2091922,
+2091950,
+2091986,
+2092013,
+2092046,
+2092081,
+2092109,
+2092142,
+2092177,
+2092228,
+2092547,
+2092580,
+2094019,
+2094084,
+2095101,
+2095172,
+2095389,
+2095428,
+2095645,
+2095684,
+2095901,
+2095940,
+2096061,
+2096147,
+2096210,
+2096244,
+2096277,
+2096307,
+2096381,
+2096405,
+2096434,
+2096565,
+2096637,
+2096954,
+2097045,
+2097117,
+2097156,
+2097565,
+2097572,
+2098429,
+2098436,
+2099069,
+2099076,
+2099165,
+2099172,
+2099677,
+2099716,
+2100189,
+2101252,
+2105213,
+2105361,
+2105469,
+2105578,
+2107037,
+2107125,
+2107401,
+2109098,
+2109237,
+2109770,
+2109821,
+2109973,
+2110365,
+2112021,
+2113445,
+2113501,
+2117636,
+2118589,
+2118660,
+2120253,
+2121732,
+2122749,
+2122762,
+2122909,
+2123268,
+2123817,
+2123844,
+2124105,
+2124157,
+2125828,
+2126813,
+2126833,
+2126852,
+2128029,
+2128132,
+2128401,
+2128425,
+2128605,
+2129920,
+2131201,
+2132484,
+2135005,
+2135048,
+2135389,
+2162692,
+2162909,
+2162948,
+2163005,
+2163012,
+2164445,
+2164452,
+2164541,
+2164612,
+2164669,
+2164708,
+2165469,
+2165489,
+2165514,
+2165789,
+2170884,
+2171594,
+2171805,
+2171889,
+2171908,
+2172765,
+2172913,
+2172957,
+2174980,
+2176797,
+2176964,
+2177053,
+2179076,
+2179109,
+2179229,
+2179237,
+2179325,
+2179461,
+2179588,
+2179741,
+2179748,
+2179869,
+2179876,
+2180765,
+2180869,
+2180989,
+2181093,
+2181130,
+2181405,
+2181649,
+2181949,
+2182148,
+2183082,
+2183153,
+2183197,
+2187268,
+2189021,
+2189105,
+2189316,
+2190045,
+2190090,
+2190340,
+2190973,
+2191114,
+2191389,
+2195460,
+2197821,
+2214922,
+2215933,
+2228230,
+2228261,
+2228294,
+2228324,
+2230021,
+2230513,
+2230749,
+2230858,
+2231496,
+2231837,
+2232325,
+2232390,
+2232420,
+2233862,
+2233957,
+2234086,
+2234149,
+2234225,
+2234298,
+2234321,
+2234461,
+2234884,
+2235709,
+2235912,
+2236253,
+2236421,
+2236516,
+2237669,
+2237830,
+2237861,
+2238141,
+2238152,
+2238481,
+2238621,
+2240517,
+2240582,
+2240612,
+2242150,
+2242245,
+2242534,
+2242596,
+2242737,
+2242877,
+2243080,
+2243421,
+2281476,
+2282853,
+2282886,
+2282917,
+2282950,
+2283013,
+2283206,
+2283237,
+2283293,
+2283528,
+2283869,
+2359300,
+2387453,
+2392073,
+2395261,
+2395665,
+2395805,
+2490372,
+2524669,
+2949124,
+2967357,
+3006468,
+3008701,
+3009028,
+3009062,
+3010557,
+3011045,
+3011171,
+3011613,
+3538948,
+3539037,
+3801109,
+3808989,
+3809301,
+3810557,
+3810613,
+3812518,
+3812581,
+3812693,
+3812774,
+3812986,
+3813221,
+3813493,
+3813541,
+3813781,
+3814725,
+3814869,
+3816413,
+3817493,
+3819589,
+3819701,
+3819741,
+3825685,
+3828477,
+3828746,
+3829341,
+3833856,
+3834689,
+3835520,
+3836353,
+3836605,
+3836609,
+3837184,
+3838017,
+3838848,
+3838909,
+3838912,
+3839005,
+3839040,
+3839101,
+3839136,
+3839229,
+3839264,
+3839421,
+3839424,
+3839681,
+3839837,
+3839841,
+3839901,
+3839905,
+3840157,
+3840161,
+3840512,
+3841345,
+3842176,
+3842269,
+3842272,
+3842429,
+3842464,
+3842749,
+3842752,
+3843005,
+3843009,
+3843840,
+3843933,
+3843936,
+3844093,
+3844096,
+3844285,
+3844288,
+3844349,
+3844416,
+3844669,
+3844673,
+3845504,
+3846337,
+3847168,
+3848001,
+3848832,
+3849665,
+3850496,
+3851329,
+3852160,
+3852993,
+3853824,
+3854657,
+3855581,
+3855616,
+3856434,
+3856449,
+3857266,
+3857281,
+3857472,
+3858290,
+3858305,
+3859122,
+3859137,
+3859328,
+3860146,
+3860161,
+3860978,
+3860993,
+3861184,
+3862002,
+3862017,
+3862834,
+3862849,
+3863040,
+3863858,
+3863873,
+3864690,
+3864705,
+3864896,
+3864929,
+3864989,
+3865032,
+3866653,
+4046852,
+4047005,
+4047012,
+4047901,
+4047908,
+4047997,
+4048004,
+4048061,
+4048100,
+4048157,
+4048164,
+4048509,
+4048516,
+4048669,
+4048676,
+4048733,
+4048740,
+4048797,
+4048964,
+4049021,
+4049124,
+4049181,
+4049188,
+4049245,
+4049252,
+4049309,
+4049316,
+4049437,
+4049444,
+4049533,
+4049540,
+4049597,
+4049636,
+4049693,
+4049700,
+4049757,
+4049764,
+4049821,
+4049828,
+4049885,
+4049892,
+4049949,
+4049956,
+4050045,
+4050052,
+4050109,
+4050148,
+4050301,
+4050308,
+4050557,
+4050564,
+4050717,
+4050724,
+4050877,
+4050884,
+4050941,
+4050948,
+4051293,
+4051300,
+4051869,
+4052004,
+4052125,
+4052132,
+4052317,
+4052324,
+4052893,
+4054546,
+4054621,
+4063253,
+4064669,
+4064789,
+4067997,
+4068373,
+4068861,
+4068917,
+4069373,
+4069429,
+4069917,
+4069941,
+4070429,
+4071434,
+4071805,
+4071957,
+4072957,
+4072981,
+4074909,
+4075029,
+4076413,
+4078805,
+4079741,
+4080149,
+4081533,
+4081685,
+4081981,
+4082197,
+4082269,
+4087829,
+4088893,
+4089365,
+4089565,
+4089589,
+4091837,
+4091925,
+4092573,
+4092949,
+4094141,
+4094165,
+4094333,
+4094997,
+4095549,
+4096021,
+4098045,
+4098069,
+4098109,
+4098133,
+4103965,
+4103989,
+4104125,
+4104213,
+4106205,
+4106261,
+4106397,
+4106773,
+4107549,
+4112245,
+4114493,
+4114613,
+4114973,
+4116501,
+4118749,
+4120597,
+4124317,
+4194308,
+5561085,
+5562372,
+5695165,
+5695492,
+5702621,
+6225924,
+6243293,
+29360186,
+29360221,
+29361178,
+29364253,
+29368325,
+29376029,
+31457308,
+33554397,
+33554460,
+35651549,
+//--Autogenerated -- end of section automatically generated
+};
+
+const int maxUnicode = 0x10ffff;
+const int maskCategory = 0x1F;
+const int nRanges = sizeof(catRanges) / sizeof(catRanges[0]);
+
+}
+
+// Each element in catRanges is the start of a range of Unicode characters in
+// one general category.
+// The value is comprised of a 21-bit character value shifted 5 bits and a 5 bit
+// category matching the CharacterCategory enumeration.
+// Initial version has 3249 entries and adds about 13K to the executable.
+// The array is in ascending order so can be searched using binary search.
+// Therefore the average call takes log2(3249) = 12 comparisons.
+// For speed, it may be an useful to make a linear table for the common values,
+// possibly for 0..0xff for most Western European text or 0..0xfff for most
+// alphabetic languages.
+
+CharacterCategory CategoriseCharacter(int character) {
+       if (character < 0 || character > maxUnicode)
+               return ccCn;
+       const int baseValue = character * (maskCategory+1) + maskCategory;
+       const int *placeAfter = std::lower_bound(catRanges, catRanges+nRanges, baseValue);
+       return static_cast<CharacterCategory>(*(placeAfter-1) & maskCategory);
+}
+
+#ifdef SCI_NAMESPACE
+}
+#endif
diff --git a/plugins/scintilla/scintilla/lexlib/CharacterCategory.h 
b/plugins/scintilla/scintilla/lexlib/CharacterCategory.h
new file mode 100644
index 0000000..c860050
--- /dev/null
+++ b/plugins/scintilla/scintilla/lexlib/CharacterCategory.h
@@ -0,0 +1,31 @@
+// Scintilla source code edit control
+/** @file CharacterCategory.h
+ ** Returns the Unicode general category of a character.
+ **/
+// Copyright 2013 by Neil Hodgson <neilh scintilla org>
+// The License.txt file describes the conditions under which this software may be distributed.
+
+#ifndef CHARACTERCATEGORY_H
+#define CHARACTERCATEGORY_H
+
+#ifdef SCI_NAMESPACE
+namespace Scintilla {
+#endif
+
+enum CharacterCategory {
+       ccLu, ccLl, ccLt, ccLm, ccLo,
+       ccMn, ccMc, ccMe,
+       ccNd, ccNl, ccNo,
+       ccPc, ccPd, ccPs, ccPe, ccPi, ccPf, ccPo,
+       ccSm, ccSc, ccSk, ccSo,
+       ccZs, ccZl, ccZp,
+       ccCc, ccCf, ccCs, ccCo, ccCn
+};
+
+CharacterCategory CategoriseCharacter(int character);
+
+#ifdef SCI_NAMESPACE
+}
+#endif
+
+#endif
diff --git a/plugins/scintilla/scintilla/lexlib/LexAccessor.h 
b/plugins/scintilla/scintilla/lexlib/LexAccessor.h
index 59ae113..e29bbc9 100644
--- a/plugins/scintilla/scintilla/lexlib/LexAccessor.h
+++ b/plugins/scintilla/scintilla/lexlib/LexAccessor.h
@@ -79,6 +79,12 @@ public:
                }
                return buf[position - startPos];
        }
+       IDocumentWithLineEnd *MultiByteAccess() const {
+               if (documentVersion >= dvLineEnd) {
+                       return static_cast<IDocumentWithLineEnd *>(pAccess);
+               }
+               return 0;
+       }
        /** Safe version of operator[], returning a defined value for invalid position. */
        char SafeGetCharAt(int position, char chDefault=' ') {
                if (position < startPos || position >= endPos) {
@@ -90,7 +96,7 @@ public:
                }
                return buf[position - startPos];
        }
-       bool IsLeadByte(char ch) {
+       bool IsLeadByte(char ch) const {
                return pAccess->IsDBCSLeadByte(ch);
        }
        EncodingType Encoding() const {
@@ -104,13 +110,13 @@ public:
                }
                return true;
        }
-       char StyleAt(int position) {
+       char StyleAt(int position) const {
                return static_cast<char>(pAccess->StyleAt(position) & mask);
        }
-       int GetLine(int position) {
+       int GetLine(int position) const {
                return pAccess->LineFromPosition(position);
        }
-       int LineStart(int line) {
+       int LineStart(int line) const {
                return pAccess->LineStart(line);
        }
        int LineEnd(int line) {
@@ -126,7 +132,7 @@ public:
                                return startNext - 1;
                }
        }
-       int LevelAt(int line) {
+       int LevelAt(int line) const {
                return pAccess->GetLevel(line);
        }
        int Length() const {
@@ -140,7 +146,7 @@ public:
                        validLen = 0;
                }
        }
-       int GetLineState(int line) {
+       int GetLineState(int line) const {
                return pAccess->GetLineState(line);
        }
        int SetLineState(int line, int state) {
diff --git a/plugins/scintilla/scintilla/lexlib/LexerModule.cxx 
b/plugins/scintilla/scintilla/lexlib/LexerModule.cxx
index defc863..b2b0f06 100644
--- a/plugins/scintilla/scintilla/lexlib/LexerModule.cxx
+++ b/plugins/scintilla/scintilla/lexlib/LexerModule.cxx
@@ -74,11 +74,9 @@ int LexerModule::GetNumWordLists() const {
 }
 
 const char *LexerModule::GetWordListDescription(int index) const {
-       static const char *emptyStr = "";
-
        assert(index < GetNumWordLists());
-       if (index >= GetNumWordLists()) {
-               return emptyStr;
+       if (!wordListDescriptions || (index >= GetNumWordLists())) {
+               return "";
        } else {
                return wordListDescriptions[index];
        }
diff --git a/plugins/scintilla/scintilla/lexlib/OptionSet.h b/plugins/scintilla/scintilla/lexlib/OptionSet.h
index 873ac8b..2935a20 100644
--- a/plugins/scintilla/scintilla/lexlib/OptionSet.h
+++ b/plugins/scintilla/scintilla/lexlib/OptionSet.h
@@ -40,7 +40,7 @@ class OptionSet {
                Option(plcos ps_, std::string description_) :
                        opType(SC_TYPE_STRING), ps(ps_), description(description_) {
                }
-               bool Set(T *base, const char *val) {
+               bool Set(T *base, const char *val) const {
                        switch (opType) {
                        case SC_TYPE_BOOLEAN: {
                                        bool option = atoi(val) != 0;
@@ -94,7 +94,7 @@ public:
                nameToDef[name] = Option(ps, description);
                AppendName(name);
        }
-       const char *PropertyNames() {
+       const char *PropertyNames() const {
                return names.c_str();
        }
        int PropertyType(const char *name) {
@@ -130,7 +130,7 @@ public:
                }
        }
 
-       const char *DescribeWordListSets() {
+       const char *DescribeWordListSets() const {
                return wordLists.c_str();
        }
 };
diff --git a/plugins/scintilla/scintilla/lexlib/PropSetSimple.cxx 
b/plugins/scintilla/scintilla/lexlib/PropSetSimple.cxx
index c0ec594..9197fb6 100644
--- a/plugins/scintilla/scintilla/lexlib/PropSetSimple.cxx
+++ b/plugins/scintilla/scintilla/lexlib/PropSetSimple.cxx
@@ -141,30 +141,21 @@ static int ExpandAllInPlace(const PropSetSimple &props, std::string &withVars, i
        return maxExpands;
 }
 
-char *PropSetSimple::Expanded(const char *key) const {
+int PropSetSimple::GetExpanded(const char *key, char *result) const {
        std::string val = Get(key);
        ExpandAllInPlace(*this, val, 100, VarChain(key));
-       char *ret = new char [val.size() + 1];
-       strcpy(ret, val.c_str());
-       return ret;
-}
-
-int PropSetSimple::GetExpanded(const char *key, char *result) const {
-       char *val = Expanded(key);
-       const int n = static_cast<int>(strlen(val));
+       const int n = static_cast<int>(val.size());
        if (result) {
-               strcpy(result, val);
+               strcpy(result, val.c_str());
        }
-       delete []val;
        return n;       // Not including NUL
 }
 
 int PropSetSimple::GetInt(const char *key, int defaultValue) const {
-       char *val = Expanded(key);
-       if (val) {
-               int retVal = val[0] ? atoi(val) : defaultValue;
-               delete []val;
-               return retVal;
+       std::string val = Get(key);
+       ExpandAllInPlace(*this, val, 100, VarChain(key));
+       if (!val.empty()) {
+               return atoi(val.c_str());
        }
        return defaultValue;
 }
diff --git a/plugins/scintilla/scintilla/lexlib/PropSetSimple.h 
b/plugins/scintilla/scintilla/lexlib/PropSetSimple.h
index b798737..8ca741f 100644
--- a/plugins/scintilla/scintilla/lexlib/PropSetSimple.h
+++ b/plugins/scintilla/scintilla/lexlib/PropSetSimple.h
@@ -21,7 +21,6 @@ public:
        void Set(const char *key, const char *val, int lenKey=-1, int lenVal=-1);
        void SetMultiple(const char *);
        const char *Get(const char *key) const;
-       char *Expanded(const char *key) const;
        int GetExpanded(const char *key, char *result) const;
        int GetInt(const char *key, int defaultValue=0) const;
 };
diff --git a/plugins/scintilla/scintilla/lexlib/StyleContext.h 
b/plugins/scintilla/scintilla/lexlib/StyleContext.h
index 9f1818f..73b7b51 100644
--- a/plugins/scintilla/scintilla/lexlib/StyleContext.h
+++ b/plugins/scintilla/scintilla/lexlib/StyleContext.h
@@ -1,5 +1,5 @@
 // Scintilla source code edit control
-/** @file StyleContext.cxx
+/** @file StyleContext.h
  ** Lexer infrastructure.
  **/
 // Copyright 1998-2004 by Neil Hodgson <neilh scintilla org>
@@ -19,83 +19,60 @@ static inline int MakeLowerCase(int ch) {
                return ch - 'A' + 'a';
 }
 
-inline int UnicodeCodePoint(const unsigned char *us) {
-       if (us[0] < 0xC2) {
-               return us[0];
-       } else if (us[0] < 0xE0) {
-               return ((us[0] & 0x1F) << 6) + (us[1] & 0x3F);
-       } else if (us[0] < 0xF0) {
-               return ((us[0] & 0xF) << 12) + ((us[1] & 0x3F) << 6) + (us[2] & 0x3F);
-       } else if (us[0] < 0xF5) {
-               return ((us[0] & 0x7) << 18) + ((us[1] & 0x3F) << 12) + ((us[2] & 0x3F) << 6) + (us[3] & 
0x3F);
-       }
-       return us[0];
-}
-
-inline int BytesInUnicodeCodePoint(int codePoint) {
-       if (codePoint < 0x80)
-               return 1;
-       else if (codePoint < 0x800)
-               return 2;
-       else if (codePoint < 0x10000)
-               return 3;
-       else
-               return 4;
-}
-
 // All languages handled so far can treat all characters >= 0x80 as one class
 // which just continues the current token or starts an identifier if in default.
 // DBCS treated specially as the second character can be < 0x80 and hence
 // syntactically significant. UTF-8 avoids this as all trail bytes are >= 0x80
 class StyleContext {
        LexAccessor &styler;
+       IDocumentWithLineEnd *multiByteAccess;
        unsigned int endPos;
+       unsigned int lengthDocument;
+       
+       // Used for optimizing GetRelativeCharacter
+       unsigned int posRelative;
+       unsigned int currentPosLastRelative;
+       int offsetRelative;
+
        StyleContext &operator=(const StyleContext &);
 
-       void GetNextChar(unsigned int pos) {
-               chNext = static_cast<unsigned char>(styler.SafeGetCharAt(pos+1));
-               if (styler.Encoding() == encUnicode) {
-                       if (chNext >= 0x80) {
-                               unsigned char bytes[4] = { static_cast<unsigned char>(chNext), 0, 0, 0 };
-                               for (int trail=1; trail<3; trail++) {
-                                       bytes[trail] = static_cast<unsigned 
char>(styler.SafeGetCharAt(pos+1+trail));
-                                       if (!((bytes[trail] >= 0x80) && (bytes[trail] < 0xc0))) {
-                                               bytes[trail] = 0;
-                                               break;
-                                       }
-                               }
-                               chNext = UnicodeCodePoint(bytes);
-                       }
-               } else if (styler.Encoding() == encDBCS) {
-                       if (styler.IsLeadByte(static_cast<char>(chNext))) {
-                               chNext = chNext << 8;
-                               chNext |= static_cast<unsigned char>(styler.SafeGetCharAt(pos+2));
-                       }
+       void GetNextChar() {
+               if (multiByteAccess) {
+                       chNext = multiByteAccess->GetCharacterAndWidth(currentPos+width, &widthNext);
+               } else {
+                       chNext = static_cast<unsigned char>(styler.SafeGetCharAt(currentPos+width, 0));
+                       widthNext = 1;
                }
-               // End of line?
-               // Trigger on CR only (Mac style) or either on LF from CR+LF (Dos/Win)
-               // or on LF alone (Unix). Avoid triggering two times on Dos/Win.
-               if (lineStartNext < styler.Length())
-                       atLineEnd = static_cast<int>(pos) >= (lineStartNext-1);
+               // End of line determined from line end position, allowing CR, LF, 
+               // CRLF and Unicode line ends as set by document.
+               if (currentLine < lineDocEnd)
+                       atLineEnd = static_cast<int>(currentPos) >= (lineStartNext-1);
                else // Last line
-                       atLineEnd = static_cast<int>(pos) >= lineStartNext;
+                       atLineEnd = static_cast<int>(currentPos) >= lineStartNext;
        }
 
 public:
        unsigned int currentPos;
        int currentLine;
+       int lineDocEnd;
        int lineStartNext;
        bool atLineStart;
        bool atLineEnd;
        int state;
        int chPrev;
        int ch;
+       int width;
        int chNext;
+       int widthNext;
 
        StyleContext(unsigned int startPos, unsigned int length,
                         int initStyle, LexAccessor &styler_, char chMask=31) :
                styler(styler_),
+               multiByteAccess(0),
                endPos(startPos + length),
+               posRelative(0),
+               currentPosLastRelative(0x7FFFFFFF),
+               offsetRelative(0),
                currentPos(startPos),
                currentLine(-1),
                lineStartNext(-1),
@@ -103,30 +80,32 @@ public:
                state(initStyle & chMask), // Mask off all bits which aren't in the chMask.
                chPrev(0),
                ch(0),
-               chNext(0) {
+               width(0),
+               chNext(0),
+               widthNext(1) {
+               if (styler.Encoding() != enc8bit) {
+                       multiByteAccess = styler.MultiByteAccess();
+               }
                styler.StartAt(startPos, chMask);
                styler.StartSegment(startPos);
                currentLine = styler.GetLine(startPos);
                lineStartNext = styler.LineStart(currentLine+1);
+               lengthDocument = static_cast<unsigned int>(styler.Length());
+               if (endPos == lengthDocument)
+                       endPos++;
+               lineDocEnd = styler.GetLine(lengthDocument);
                atLineStart = static_cast<unsigned int>(styler.LineStart(currentLine)) == startPos;
-               unsigned int pos = currentPos;
-               ch = static_cast<unsigned char>(styler.SafeGetCharAt(pos));
-               if (styler.Encoding() == encUnicode) {
-                       // Get the current char
-                       GetNextChar(pos-1);
-                       ch = chNext;
-                       pos += BytesInUnicodeCodePoint(ch) - 1;
-               } else if (styler.Encoding() == encDBCS) {
-                       if (styler.IsLeadByte(static_cast<char>(ch))) {
-                               pos++;
-                               ch = ch << 8;
-                               ch |= static_cast<unsigned char>(styler.SafeGetCharAt(pos));
-                       }
-               }
-               GetNextChar(pos);
+
+               // Variable width is now 0 so GetNextChar gets the char at currentPos into chNext/widthNext
+               width = 0;
+               GetNextChar();
+               ch = chNext;
+               width = widthNext;
+
+               GetNextChar();
        }
        void Complete() {
-               styler.ColourTo(currentPos - 1, state);
+               styler.ColourTo(currentPos - ((currentPos > lengthDocument) ? 2 : 1), state);
                styler.Flush();
        }
        bool More() const {
@@ -140,23 +119,10 @@ public:
                                lineStartNext = styler.LineStart(currentLine+1);
                        }
                        chPrev = ch;
-                       if (styler.Encoding() == encUnicode) {
-                               currentPos += BytesInUnicodeCodePoint(ch);
-                       } else if (styler.Encoding() == encDBCS) {
-                               currentPos++;
-                               if (ch >= 0x100)
-                                       currentPos++;
-                       } else {
-                               currentPos++;
-                       }
+                       currentPos += width;
                        ch = chNext;
-                       if (styler.Encoding() == encUnicode) {
-                               GetNextChar(currentPos + BytesInUnicodeCodePoint(ch)-1);
-                       } else if (styler.Encoding() == encDBCS) {
-                               GetNextChar(currentPos + ((ch >= 0x100) ? 1 : 0));
-                       } else {
-                               GetNextChar(currentPos);
-                       }
+                       width = widthNext;
+                       GetNextChar();
                } else {
                        atLineStart = false;
                        chPrev = ' ';
@@ -170,23 +136,51 @@ public:
                        Forward();
                }
        }
+       void ForwardBytes(int nb) {
+               size_t forwardPos = currentPos + nb;
+               while (forwardPos > currentPos) {
+                       Forward();
+               }
+       }
        void ChangeState(int state_) {
                state = state_;
        }
        void SetState(int state_) {
-               styler.ColourTo(currentPos - 1, state);
+               styler.ColourTo(currentPos - ((currentPos > lengthDocument) ? 2 : 1), state);
                state = state_;
        }
        void ForwardSetState(int state_) {
                Forward();
-               styler.ColourTo(currentPos - 1, state);
+               styler.ColourTo(currentPos - ((currentPos > lengthDocument) ? 2 : 1), state);
                state = state_;
        }
-       int LengthCurrent() {
+       int LengthCurrent() const {
                return currentPos - styler.GetStartSegment();
        }
        int GetRelative(int n) {
-               return static_cast<unsigned char>(styler.SafeGetCharAt(currentPos+n));
+               return static_cast<unsigned char>(styler.SafeGetCharAt(currentPos+n, 0));
+       }
+       int GetRelativeCharacter(int n) {
+               if (n == 0)
+                       return ch;
+               if (multiByteAccess) {
+                       if ((currentPosLastRelative != currentPos) ||
+                               ((n > 0) && ((offsetRelative < 0) || (n < offsetRelative))) ||
+                               ((n < 0) && ((offsetRelative > 0) || (n > offsetRelative)))) {
+                               posRelative = currentPos;
+                               offsetRelative = 0;
+                       }
+                       int diffRelative = n - offsetRelative;
+                       int posNew = multiByteAccess->GetRelativePosition(posRelative, diffRelative);
+                       int ch = multiByteAccess->GetCharacterAndWidth(posNew, 0);
+                       posRelative = posNew;
+                       currentPosLastRelative = currentPos;
+                       offsetRelative = n;
+                       return ch;
+               } else {
+                       // fast version for single byte encodings
+                       return static_cast<unsigned char>(styler.SafeGetCharAt(currentPos + n, 0));
+               }
        }
        bool Match(char ch0) const {
                return ch == static_cast<unsigned char>(ch0);
@@ -204,7 +198,7 @@ public:
                        return false;
                s++;
                for (int n=2; *s; n++) {
-                       if (*s != styler.SafeGetCharAt(currentPos+n))
+                       if (*s != styler.SafeGetCharAt(currentPos+n, 0))
                                return false;
                        s++;
                }
@@ -219,7 +213,7 @@ public:
                s++;
                for (int n=2; *s; n++) {
                        if (static_cast<unsigned char>(*s) !=
-                               MakeLowerCase(static_cast<unsigned char>(styler.SafeGetCharAt(currentPos+n))))
+                               MakeLowerCase(static_cast<unsigned char>(styler.SafeGetCharAt(currentPos+n, 
0))))
                                return false;
                        s++;
                }
diff --git a/plugins/scintilla/scintilla/lexlib/WordList.cxx b/plugins/scintilla/scintilla/lexlib/WordList.cxx
index 9c2c965..049bf6e 100644
--- a/plugins/scintilla/scintilla/lexlib/WordList.cxx
+++ b/plugins/scintilla/scintilla/lexlib/WordList.cxx
@@ -45,29 +45,37 @@ static char **ArrayFromWordList(char *wordlist, int *len, bool onlyLineEnds = fa
                prev = curr;
        }
        char **keywords = new char *[words + 1];
-       if (keywords) {
-               words = 0;
-               prev = '\0';
-               size_t slen = strlen(wordlist);
-               for (size_t k = 0; k < slen; k++) {
-                       if (!wordSeparator[static_cast<unsigned char>(wordlist[k])]) {
-                               if (!prev) {
-                                       keywords[words] = &wordlist[k];
-                                       words++;
-                               }
-                       } else {
-                               wordlist[k] = '\0';
+       words = 0;
+       prev = '\0';
+       size_t slen = strlen(wordlist);
+       for (size_t k = 0; k < slen; k++) {
+               if (!wordSeparator[static_cast<unsigned char>(wordlist[k])]) {
+                       if (!prev) {
+                               keywords[words] = &wordlist[k];
+                               words++;
                        }
-                       prev = wordlist[k];
+               } else {
+                       wordlist[k] = '\0';
                }
-               keywords[words] = &wordlist[slen];
-               *len = words;
-       } else {
-               *len = 0;
+               prev = wordlist[k];
        }
+       keywords[words] = &wordlist[slen];
+       *len = words;
        return keywords;
 }
 
+WordList::WordList(bool onlyLineEnds_) :
+       words(0), list(0), len(0), onlyLineEnds(onlyLineEnds_) {
+}
+
+WordList::~WordList() { 
+       Clear();
+}
+
+WordList::operator bool() const {
+       return len ? true : false;
+}
+
 bool WordList::operator!=(const WordList &other) const {
        if (len != other.len)
                return true;
@@ -78,6 +86,10 @@ bool WordList::operator!=(const WordList &other) const {
        return false;
 }
 
+int WordList::Length() const {
+       return len;
+}
+
 void WordList::Clear() {
        if (words) {
                delete []list;
@@ -217,3 +229,8 @@ bool WordList::InListAbbreviated(const char *s, const char marker) const {
        }
        return false;
 }
+
+const char *WordList::WordAt(int n) const {
+       return words[n];
+}
+
diff --git a/plugins/scintilla/scintilla/lexlib/WordList.h b/plugins/scintilla/scintilla/lexlib/WordList.h
index ea5be1d..9c8285e 100644
--- a/plugins/scintilla/scintilla/lexlib/WordList.h
+++ b/plugins/scintilla/scintilla/lexlib/WordList.h
@@ -15,23 +15,23 @@ namespace Scintilla {
 /**
  */
 class WordList {
-public:
        // Each word contains at least one character - a empty word acts as sentinel at the end.
        char **words;
        char *list;
        int len;
        bool onlyLineEnds;      ///< Delimited by any white space or only line ends
        int starts[256];
-       WordList(bool onlyLineEnds_ = false) :
-               words(0), list(0), len(0), onlyLineEnds(onlyLineEnds_)
-               {}
-       ~WordList() { Clear(); }
-       operator bool() const { return len ? true : false; }
+public:
+       WordList(bool onlyLineEnds_ = false);
+       ~WordList();
+       operator bool() const;
        bool operator!=(const WordList &other) const;
+       int Length() const;
        void Clear();
        void Set(const char *s);
        bool InList(const char *s) const;
        bool InListAbbreviated(const char *s, const char marker) const;
+       const char *WordAt(int n) const;
 };
 
 #ifdef SCI_NAMESPACE
diff --git a/plugins/scintilla/scintilla/src/AutoComplete.cxx 
b/plugins/scintilla/scintilla/src/AutoComplete.cxx
index bab123a..d55af85 100644
--- a/plugins/scintilla/scintilla/src/AutoComplete.cxx
+++ b/plugins/scintilla/scintilla/src/AutoComplete.cxx
@@ -10,7 +10,9 @@
 #include <stdio.h>
 #include <assert.h>
 
+#include <algorithm>
 #include <string>
+#include <vector>
 
 #include "Platform.h"
 
@@ -36,7 +38,8 @@ AutoComplete::AutoComplete() :
        dropRestOfWord(false),
        ignoreCaseBehaviour(SC_CASEINSENSITIVEBEHAVIOUR_RESPECTCASE),
        widthLBDefault(100),
-       heightLBDefault(100) {
+       heightLBDefault(100),
+       autoSort(SC_ORDER_PRESORTED) {
        lb = ListBox::Allocate();
        stopChars[0] = '\0';
        fillUpChars[0] = '\0';
@@ -101,8 +104,91 @@ char AutoComplete::GetTypesep() const {
        return typesep;
 }
 
+struct Sorter {
+       AutoComplete *ac;
+       const char *list;
+       std::vector<int> indices;
+
+       Sorter(AutoComplete *ac_, const char *list_) : ac(ac_), list(list_) {
+               int i = 0;
+               while (list[i]) {
+                       indices.push_back(i); // word start
+                       while (list[i] != ac->GetTypesep() && list[i] != ac->GetSeparator() && list[i])
+                               ++i;
+                       indices.push_back(i); // word end
+                       if (list[i] == ac->GetTypesep()) {
+                               while (list[i] != ac->GetSeparator() && list[i])
+                                       ++i;
+                       }
+                       if (list[i] == ac->GetSeparator()) {
+                               ++i;
+                               // preserve trailing separator as blank entry
+                               if (!list[i]) {
+                                       indices.push_back(i);
+                                       indices.push_back(i);
+                               }
+                       }
+               }
+               indices.push_back(i); // index of last position
+       }
+
+       bool operator()(int a, int b) {
+               int lenA = indices[a * 2 + 1] - indices[a * 2];
+               int lenB = indices[b * 2 + 1] - indices[b * 2];
+               int len  = std::min(lenA, lenB);
+               int cmp;
+               if (ac->ignoreCase)
+                       cmp = CompareNCaseInsensitive(list + indices[a * 2], list + indices[b * 2], len);
+               else
+                       cmp = strncmp(list + indices[a * 2], list + indices[b * 2], len);
+               if (cmp == 0)
+                       cmp = lenA - lenB;
+               return cmp < 0;
+       }
+};
+
 void AutoComplete::SetList(const char *list) {
-       lb->SetList(list, separator, typesep);
+       if (autoSort == SC_ORDER_PRESORTED) {
+               lb->SetList(list, separator, typesep);
+               sortMatrix.clear();
+               for (int i = 0; i < lb->Length(); ++i)
+                       sortMatrix.push_back(i);
+               return;
+       }
+
+       Sorter IndexSort(this, list);
+       sortMatrix.clear();
+       for (int i = 0; i < (int)IndexSort.indices.size() / 2; ++i)
+               sortMatrix.push_back(i);
+       std::sort(sortMatrix.begin(), sortMatrix.end(), IndexSort);
+       if (autoSort == SC_ORDER_CUSTOM || sortMatrix.size() < 2) {
+               lb->SetList(list, separator, typesep);
+               PLATFORM_ASSERT(lb->Length() == static_cast<int>(sortMatrix.size()));
+               return;
+       }
+
+       std::string sortedList;
+       char item[maxItemLen];
+       for (size_t i = 0; i < sortMatrix.size(); ++i) {
+               int wordLen = IndexSort.indices[sortMatrix[i] * 2 + 2] - IndexSort.indices[sortMatrix[i] * 2];
+               strncpy(item, list + IndexSort.indices[sortMatrix[i] * 2], wordLen);
+               if ((i+1) == sortMatrix.size()) {
+                       // Last item so remove separator if present
+                       if ((wordLen > 0) && (item[wordLen-1] == separator))
+                               wordLen--;
+               } else {
+                       // Item before last needs a separator
+                       if ((wordLen == 0) || (item[wordLen-1] != separator)) {
+                               item[wordLen] = separator;
+                               wordLen++;
+                       }
+               }
+               item[wordLen] = '\0';
+               sortedList += item;
+       }
+       for (int i = 0; i < (int)sortMatrix.size(); ++i)
+               sortMatrix[i] = i;
+       lb->SetList(sortedList.c_str(), separator, typesep);
 }
 
 int AutoComplete::GetSelection() const {
@@ -149,7 +235,7 @@ void AutoComplete::Select(const char *word) {
        while ((start <= end) && (location == -1)) { // Binary searching loop
                int pivot = (start + end) / 2;
                char item[maxItemLen];
-               lb->GetValue(pivot, item, maxItemLen);
+               lb->GetValue(sortMatrix[pivot], item, maxItemLen);
                int cond;
                if (ignoreCase)
                        cond = CompareNCaseInsensitive(word, item, lenWord);
@@ -158,7 +244,7 @@ void AutoComplete::Select(const char *word) {
                if (!cond) {
                        // Find first match
                        while (pivot > start) {
-                               lb->GetValue(pivot-1, item, maxItemLen);
+                               lb->GetValue(sortMatrix[pivot-1], item, maxItemLen);
                                if (ignoreCase)
                                        cond = CompareNCaseInsensitive(word, item, lenWord);
                                else
@@ -172,7 +258,7 @@ void AutoComplete::Select(const char *word) {
                                && ignoreCaseBehaviour == SC_CASEINSENSITIVEBEHAVIOUR_RESPECTCASE) {
                                // Check for exact-case match
                                for (; pivot <= end; pivot++) {
-                                       lb->GetValue(pivot, item, maxItemLen);
+                                       lb->GetValue(sortMatrix[pivot], item, maxItemLen);
                                        if (!strncmp(word, item, lenWord)) {
                                                location = pivot;
                                                break;
@@ -187,9 +273,24 @@ void AutoComplete::Select(const char *word) {
                        start = pivot + 1;
                }
        }
-       if (location == -1 && autoHide)
-               Cancel();
-       else
-               lb->Select(location);
+       if (location == -1) {
+               if (autoHide)
+                       Cancel();
+               else
+                       lb->Select(-1);
+       } else {
+               if (autoSort == SC_ORDER_CUSTOM) {
+                       // Check for a logically earlier match
+                       char item[maxItemLen];
+                       for (int i = location + 1; i <= end; ++i) {
+                               lb->GetValue(sortMatrix[i], item, maxItemLen);
+                               if (CompareNCaseInsensitive(word, item, lenWord))
+                                       break;
+                               if (sortMatrix[i] < sortMatrix[location] && !strncmp(word, item, lenWord))
+                                       location = i;
+                       }
+               }
+               lb->Select(sortMatrix[location]);
+       }
 }
 
diff --git a/plugins/scintilla/scintilla/src/AutoComplete.h b/plugins/scintilla/scintilla/src/AutoComplete.h
index 4d27e6a..9977196 100644
--- a/plugins/scintilla/scintilla/src/AutoComplete.h
+++ b/plugins/scintilla/scintilla/src/AutoComplete.h
@@ -21,6 +21,7 @@ class AutoComplete {
        char separator;
        char typesep; // Type seperator
        enum { maxItemLen=1000 };
+       std::vector<int> sortMatrix;
 
 public:
 
@@ -36,6 +37,11 @@ public:
        unsigned int ignoreCaseBehaviour;
        int widthLBDefault;
        int heightLBDefault;
+       /** SC_ORDER_PRESORTED:   Assume the list is presorted; selection will fail if it is not 
alphabetical<br />
+        *  SC_ORDER_PERFORMSORT: Sort the list alphabetically; start up performance cost for sorting<br />
+        *  SC_ORDER_CUSTOM:      Handle non-alphabetical entries; start up performance cost for generating a 
sorted lookup table
+        */
+       int autoSort;
 
        AutoComplete();
        ~AutoComplete();
diff --git a/plugins/scintilla/scintilla/src/CallTip.cxx b/plugins/scintilla/scintilla/src/CallTip.cxx
index d5ba3bd..c12a6e8 100644
--- a/plugins/scintilla/scintilla/src/CallTip.cxx
+++ b/plugins/scintilla/scintilla/src/CallTip.cxx
@@ -7,12 +7,14 @@
 
 #include <stdlib.h>
 #include <string.h>
+#include <stdio.h>
+
+#include <string>
 
 #include "Platform.h"
 
 #include "Scintilla.h"
 #include "CallTip.h"
-#include <stdio.h>
 
 #ifdef SCI_NAMESPACE
 using namespace Scintilla;
@@ -22,7 +24,6 @@ CallTip::CallTip() {
        wCallTip = 0;
        inCallTipMode = false;
        posStartCallTip = 0;
-       val = 0;
        rectUp = PRectangle(0,0,0,0);
        rectDown = PRectangle(0,0,0,0);
        lineHeight = 1;
@@ -56,8 +57,6 @@ CallTip::CallTip() {
 CallTip::~CallTip() {
        font.Release();
        wCallTip.Destroy();
-       delete []val;
-       val = 0;
 }
 
 // Although this test includes 0, we should never see a \0 character.
@@ -70,7 +69,7 @@ bool CallTip::IsTabCharacter(char ch) const {
        return (tabSize > 0) && (ch == '\t');
 }
 
-int CallTip::NextTabPos(int x) {
+int CallTip::NextTabPos(int x) const {
        if (tabSize > 0) {              // paranoia... not called unless this is true
                x -= insetX;                // position relative to text
                x = (x + tabSize) / tabSize;  // tab "number"
@@ -176,17 +175,17 @@ int CallTip::PaintContents(Surface *surfaceWindow, bool draw) {
        // Draw the definition in three parts: before highlight, highlighted, after highlight
        int ytext = rcClient.top + ascent + 1;
        rcClient.bottom = ytext + surfaceWindow->Descent(font) + 1;
-       char *chunkVal = val;
+       const char *chunkVal = val.c_str();
        bool moreChunks = true;
        int maxWidth = 0;
 
        while (moreChunks) {
-               char *chunkEnd = strchr(chunkVal, '\n');
+               const char *chunkEnd = strchr(chunkVal, '\n');
                if (chunkEnd == NULL) {
                        chunkEnd = chunkVal + strlen(chunkVal);
                        moreChunks = false;
                }
-               int chunkOffset = chunkVal - val;
+               int chunkOffset = chunkVal - val.c_str();
                int chunkLength = chunkEnd - chunkVal;
                int chunkEndOffset = chunkOffset + chunkLength;
                int thisStartHighlight = Platform::Maximum(startHighlight, chunkOffset);
@@ -215,7 +214,7 @@ int CallTip::PaintContents(Surface *surfaceWindow, bool draw) {
 }
 
 void CallTip::PaintCT(Surface *surfaceWindow) {
-       if (!val)
+       if (val.empty())
                return;
        PRectangle rcClientPos = wCallTip.GetClientPosition();
        PRectangle rcClientSize(0, 0, rcClientPos.right - rcClientPos.left,
@@ -253,10 +252,7 @@ PRectangle CallTip::CallTipStart(int pos, Point pt, int textHeight, const char *
                                  int codePage_, int characterSet,
                                                                 int technology, Window &wParent) {
        clickPlace = 0;
-       delete []val;
-       val = 0;
-       val = new char[strlen(defn) + 1];
-       strcpy(val, defn);
+       val = defn;
        codePage = codePage_;
        Surface *surfaceMeasure = Surface::Allocate(technology);
        if (!surfaceMeasure)
@@ -275,7 +271,7 @@ PRectangle CallTip::CallTipStart(int pos, Point pt, int textHeight, const char *
        // Only support \n here - simply means container must avoid \r!
        int numLines = 1;
        const char *newline;
-       const char *look = val;
+       const char *look = val.c_str();
        rectUp = PRectangle(0,0,0,0);
        rectDown = PRectangle(0,0,0,0);
        offsetMain = insetX;            // changed to right edge of any arrows
diff --git a/plugins/scintilla/scintilla/src/CallTip.h b/plugins/scintilla/scintilla/src/CallTip.h
index fdc4db8..840aa26 100644
--- a/plugins/scintilla/scintilla/src/CallTip.h
+++ b/plugins/scintilla/scintilla/src/CallTip.h
@@ -17,7 +17,7 @@ namespace Scintilla {
 class CallTip {
        int startHighlight;    // character offset to start and...
        int endHighlight;      // ...end of highlighted text
-       char *val;
+       std::string val;
        Font font;
        PRectangle rectUp;      // rectangle of last up angle in the tip
        PRectangle rectDown;    // rectangle of last down arrow in the tip
@@ -35,7 +35,7 @@ class CallTip {
                bool highlight, bool draw);
        int PaintContents(Surface *surfaceWindow, bool draw);
        bool IsTabCharacter(char c) const;
-       int NextTabPos(int x);
+       int NextTabPos(int x) const;
 
 public:
        Window wCallTip;
diff --git a/plugins/scintilla/scintilla/src/CaseConvert.cxx b/plugins/scintilla/scintilla/src/CaseConvert.cxx
new file mode 100644
index 0000000..6f43df8
--- /dev/null
+++ b/plugins/scintilla/scintilla/src/CaseConvert.cxx
@@ -0,0 +1,630 @@
+// Scintilla source code edit control
+// Encoding: UTF-8
+/** @file CaseConvert.cxx
+ ** Case fold characters and convert them to upper or lower case.
+ ** Tables automatically regenerated by scripts/GenerateCharacterCategory.py
+ ** Should only be rarely regenerated for new versions of Unicode.
+ **/
+// Copyright 2013 by Neil Hodgson <neilh scintilla org>
+// The License.txt file describes the conditions under which this software may be distributed.
+
+#include <cstring>
+
+#include <vector>
+#include <algorithm>
+
+#include "CaseConvert.h"
+#include "UniConversion.h"
+#include "UnicodeFromUTF8.h"
+
+#ifdef SCI_NAMESPACE
+using namespace Scintilla;
+#endif
+
+namespace {
+       // Use an unnamed namespace to protect the declarations from name conflicts
+
+// Unicode code points are ordered by groups and follow patterns.
+// Most characters (pitch==1) are in ranges for a particular alphabet and their
+// upper case forms are a fixed distance away.
+// Another pattern (pitch==2) is where each lower case letter is preceded by
+// the upper case form. These are also grouped into ranges.
+
+int symmetricCaseConversionRanges[] = {
+//lower, upper, range length, range pitch
+//++Autogenerated -- start of section automatically generated
+//**\(\*\n\)
+97,65,26,1, 
+224,192,23,1, 
+248,216,7,1, 
+257,256,24,2, 
+314,313,8,2, 
+331,330,23,2, 
+462,461,8,2, 
+479,478,9,2, 
+505,504,20,2, 
+547,546,9,2, 
+583,582,5,2, 
+945,913,17,1, 
+963,931,9,1, 
+985,984,12,2, 
+1072,1040,32,1, 
+1104,1024,16,1, 
+1121,1120,17,2, 
+1163,1162,27,2, 
+1218,1217,7,2, 
+1233,1232,44,2, 
+1377,1329,38,1, 
+7681,7680,75,2, 
+7841,7840,48,2, 
+7936,7944,8,1, 
+7952,7960,6,1, 
+7968,7976,8,1, 
+7984,7992,8,1, 
+8000,8008,6,1, 
+8032,8040,8,1, 
+8560,8544,16,1, 
+9424,9398,26,1, 
+11312,11264,47,1, 
+11393,11392,50,2, 
+11520,4256,38,1, 
+42561,42560,23,2, 
+42625,42624,12,2, 
+42787,42786,7,2, 
+42803,42802,31,2, 
+42879,42878,5,2, 
+42913,42912,5,2, 
+65345,65313,26,1, 
+66600,66560,40,1, 
+
+//--Autogenerated -- end of section automatically generated
+};
+
+// Code points that are symmetric but don't fit into a range of similar characters
+// are listed here.
+
+int symmetricCaseConversions[] = {
+//lower, upper
+//++Autogenerated -- start of section automatically generated
+//**1 \(\*\n\)
+255,376, 
+307,306, 
+309,308, 
+311,310, 
+378,377, 
+380,379, 
+382,381, 
+384,579, 
+387,386, 
+389,388, 
+392,391, 
+396,395, 
+402,401, 
+405,502, 
+409,408, 
+410,573, 
+414,544, 
+417,416, 
+419,418, 
+421,420, 
+424,423, 
+429,428, 
+432,431, 
+436,435, 
+438,437, 
+441,440, 
+445,444, 
+447,503, 
+454,452, 
+457,455, 
+460,458, 
+477,398, 
+499,497, 
+501,500, 
+572,571, 
+575,11390, 
+576,11391, 
+578,577, 
+592,11375, 
+593,11373, 
+594,11376, 
+595,385, 
+596,390, 
+598,393, 
+599,394, 
+601,399, 
+603,400, 
+608,403, 
+611,404, 
+613,42893, 
+614,42922, 
+616,407, 
+617,406, 
+619,11362, 
+623,412, 
+625,11374, 
+626,413, 
+629,415, 
+637,11364, 
+640,422, 
+643,425, 
+648,430, 
+649,580, 
+650,433, 
+651,434, 
+652,581, 
+658,439, 
+881,880, 
+883,882, 
+887,886, 
+891,1021, 
+892,1022, 
+893,1023, 
+940,902, 
+941,904, 
+942,905, 
+943,906, 
+972,908, 
+973,910, 
+974,911, 
+983,975, 
+1010,1017, 
+1016,1015, 
+1019,1018, 
+1231,1216, 
+7545,42877, 
+7549,11363, 
+8017,8025, 
+8019,8027, 
+8021,8029, 
+8023,8031, 
+8048,8122, 
+8049,8123, 
+8050,8136, 
+8051,8137, 
+8052,8138, 
+8053,8139, 
+8054,8154, 
+8055,8155, 
+8056,8184, 
+8057,8185, 
+8058,8170, 
+8059,8171, 
+8060,8186, 
+8061,8187, 
+8112,8120, 
+8113,8121, 
+8144,8152, 
+8145,8153, 
+8160,8168, 
+8161,8169, 
+8165,8172, 
+8526,8498, 
+8580,8579, 
+11361,11360, 
+11365,570, 
+11366,574, 
+11368,11367, 
+11370,11369, 
+11372,11371, 
+11379,11378, 
+11382,11381, 
+11500,11499, 
+11502,11501, 
+11507,11506, 
+11559,4295, 
+11565,4301, 
+42874,42873, 
+42876,42875, 
+42892,42891, 
+42897,42896, 
+42899,42898, 
+
+//--Autogenerated -- end of section automatically generated
+};
+
+// Characters that have complex case conversions are listed here.
+// This includes cases where more than one character is needed for a conversion,
+// folding is different to lowering, or (as appropriate) upper(lower(x)) != x or
+// lower(upper(x)) != x.
+
+const char *complexCaseConversions =
+// Original | Folded | Upper | Lower |
+//++Autogenerated -- start of section automatically generated
+//**2 \(\*\n\)
+"µ|μ|Μ||"
+"ß|ss|SS||"
+"İ|i̇||i̇|"
+"ı||I||"
+"ʼn|ʼn|ʼN||"
+"ſ|s|S||"
+"Dž|dž|DŽ|dž|"
+"Lj|lj|LJ|lj|"
+"Nj|nj|NJ|nj|"
+"ǰ|ǰ|J̌||"
+"Dz|dz|DZ|dz|"
+"ͅ|ι|Ι||"
+"ΐ|ΐ|Ϊ́||"
+"ΰ|ΰ|Ϋ́||"
+"ς|σ|Σ||"
+"ϐ|β|Β||"
+"ϑ|θ|Θ||"
+"ϕ|φ|Φ||"
+"ϖ|π|Π||"
+"ϰ|κ|Κ||"
+"ϱ|ρ|Ρ||"
+"ϴ|θ||θ|"
+"ϵ|ε|Ε||"
+"և|եւ|ԵՒ||"
+"ẖ|ẖ|H̱||"
+"ẗ|ẗ|T̈||"
+"ẘ|ẘ|W̊||"
+"ẙ|ẙ|Y̊||"
+"ẚ|aʾ|Aʾ||"
+"ẛ|ṡ|Ṡ||"
+"ẞ|ss||ß|"
+"ὐ|ὐ|Υ̓||"
+"ὒ|ὒ|Υ̓̀||"
+"ὔ|ὔ|Υ̓́||"
+"ὖ|ὖ|Υ̓͂||"
+"ᾀ|ἀι|ἈΙ||"
+"ᾁ|ἁι|ἉΙ||"
+"ᾂ|ἂι|ἊΙ||"
+"ᾃ|ἃι|ἋΙ||"
+"ᾄ|ἄι|ἌΙ||"
+"ᾅ|ἅι|ἍΙ||"
+"ᾆ|ἆι|ἎΙ||"
+"ᾇ|ἇι|ἏΙ||"
+"ᾈ|ἀι|ἈΙ|ᾀ|"
+"ᾉ|ἁι|ἉΙ|ᾁ|"
+"ᾊ|ἂι|ἊΙ|ᾂ|"
+"ᾋ|ἃι|ἋΙ|ᾃ|"
+"ᾌ|ἄι|ἌΙ|ᾄ|"
+"ᾍ|ἅι|ἍΙ|ᾅ|"
+"ᾎ|ἆι|ἎΙ|ᾆ|"
+"ᾏ|ἇι|ἏΙ|ᾇ|"
+"ᾐ|ἠι|ἨΙ||"
+"ᾑ|ἡι|ἩΙ||"
+"ᾒ|ἢι|ἪΙ||"
+"ᾓ|ἣι|ἫΙ||"
+"ᾔ|ἤι|ἬΙ||"
+"ᾕ|ἥι|ἭΙ||"
+"ᾖ|ἦι|ἮΙ||"
+"ᾗ|ἧι|ἯΙ||"
+"ᾘ|ἠι|ἨΙ|ᾐ|"
+"ᾙ|ἡι|ἩΙ|ᾑ|"
+"ᾚ|ἢι|ἪΙ|ᾒ|"
+"ᾛ|ἣι|ἫΙ|ᾓ|"
+"ᾜ|ἤι|ἬΙ|ᾔ|"
+"ᾝ|ἥι|ἭΙ|ᾕ|"
+"ᾞ|ἦι|ἮΙ|ᾖ|"
+"ᾟ|ἧι|ἯΙ|ᾗ|"
+"ᾠ|ὠι|ὨΙ||"
+"ᾡ|ὡι|ὩΙ||"
+"ᾢ|ὢι|ὪΙ||"
+"ᾣ|ὣι|ὫΙ||"
+"ᾤ|ὤι|ὬΙ||"
+"ᾥ|ὥι|ὭΙ||"
+"ᾦ|ὦι|ὮΙ||"
+"ᾧ|ὧι|ὯΙ||"
+"ᾨ|ὠι|ὨΙ|ᾠ|"
+"ᾩ|ὡι|ὩΙ|ᾡ|"
+"ᾪ|ὢι|ὪΙ|ᾢ|"
+"ᾫ|ὣι|ὫΙ|ᾣ|"
+"ᾬ|ὤι|ὬΙ|ᾤ|"
+"ᾭ|ὥι|ὭΙ|ᾥ|"
+"ᾮ|ὦι|ὮΙ|ᾦ|"
+"ᾯ|ὧι|ὯΙ|ᾧ|"
+"ᾲ|ὰι|ᾺΙ||"
+"ᾳ|αι|ΑΙ||"
+"ᾴ|άι|ΆΙ||"
+"ᾶ|ᾶ|Α͂||"
+"ᾷ|ᾶι|Α͂Ι||"
+"ᾼ|αι|ΑΙ|ᾳ|"
+"ι|ι|Ι||"
+"ῂ|ὴι|ῊΙ||"
+"ῃ|ηι|ΗΙ||"
+"ῄ|ήι|ΉΙ||"
+"ῆ|ῆ|Η͂||"
+"ῇ|ῆι|Η͂Ι||"
+"ῌ|ηι|ΗΙ|ῃ|"
+"ῒ|ῒ|Ϊ̀||"
+"ΐ|ΐ|Ϊ́||"
+"ῖ|ῖ|Ι͂||"
+"ῗ|ῗ|Ϊ͂||"
+"ῢ|ῢ|Ϋ̀||"
+"ΰ|ΰ|Ϋ́||"
+"ῤ|ῤ|Ρ̓||"
+"ῦ|ῦ|Υ͂||"
+"ῧ|ῧ|Ϋ͂||"
+"ῲ|ὼι|ῺΙ||"
+"ῳ|ωι|ΩΙ||"
+"ῴ|ώι|ΏΙ||"
+"ῶ|ῶ|Ω͂||"
+"ῷ|ῶι|Ω͂Ι||"
+"ῼ|ωι|ΩΙ|ῳ|"
+"Ω|ω||ω|"
+"K|k||k|"
+"Å|å||å|"
+"ff|ff|FF||"
+"fi|fi|FI||"
+"fl|fl|FL||"
+"ffi|ffi|FFI||"
+"ffl|ffl|FFL||"
+"ſt|st|ST||"
+"st|st|ST||"
+"ﬓ|մն|ՄՆ||"
+"ﬔ|մե|ՄԵ||"
+"ﬕ|մի|ՄԻ||"
+"ﬖ|վն|ՎՆ||"
+"ﬗ|մխ|ՄԽ||"
+
+//--Autogenerated -- end of section automatically generated
+;
+
+class CaseConverter : public ICaseConverter {
+       // Maximum length of a case conversion result is 6 bytes in UTF-8
+       enum { maxConversionLength=6 };
+       struct ConversionString {
+               char conversion[maxConversionLength+1];
+       };
+       // Conversions are initially store in a vector of structs but then decomposed into
+       // parallel arrays as that is about 10% faster to search.
+       struct CharacterConversion {
+               int character;
+               ConversionString conversion;
+               CharacterConversion(int character_=0, const char *conversion_="") : character(character_) {
+                       strcpy(conversion.conversion, conversion_);
+               }
+               bool operator<(const CharacterConversion &other) const {
+                       return character < other.character;
+               }
+       };
+       typedef std::vector<CharacterConversion> CharacterToConversion;
+       CharacterToConversion characterToConversion;
+       // The parallel arrays 
+       std::vector<int> characters;
+       std::vector<ConversionString> conversions;
+
+public:
+       CaseConverter() {
+       }
+       bool Initialised() const {
+               return characters.size() > 0;
+       }
+       void Add(int character, const char *conversion) {
+               characterToConversion.push_back(CharacterConversion(character, conversion));
+       }
+       const char *Find(int character) {
+               const std::vector<int>::iterator it = std::lower_bound(characters.begin(), characters.end(), 
character);
+               if (it == characters.end())
+                       return 0;
+               else if (*it == character)
+                       return conversions[it - characters.begin()].conversion;
+               else
+                       return 0;
+       }
+       size_t CaseConvertString(char *converted, size_t sizeConverted, const char *mixed, size_t lenMixed) {
+               size_t lenConverted = 0;
+               size_t mixedPos = 0;
+               unsigned char bytes[UTF8MaxBytes + 1];
+               while (mixedPos < lenMixed) {
+                       const unsigned char leadByte = static_cast<unsigned char>(mixed[mixedPos]);
+                       const char *caseConverted = 0;
+                       size_t lenMixedChar = 1;
+                       if (UTF8IsAscii(leadByte)) {
+                               caseConverted = Find(leadByte);
+                       } else {
+                               bytes[0] = leadByte;
+                               const int widthCharBytes = UTF8BytesOfLead[leadByte];
+                               for (int b=1; b<widthCharBytes; b++) {
+                                       bytes[b] = (mixedPos+b < lenMixed) ? mixed[mixedPos+b] : 0;
+                               }
+                               int classified = UTF8Classify(bytes, widthCharBytes);
+                               if (!(classified & UTF8MaskInvalid)) {
+                                       // valid UTF-8
+                                       lenMixedChar = classified & UTF8MaskWidth;
+                                       int character = UnicodeFromUTF8(bytes);
+                                       caseConverted = Find(character);
+                               }
+                       }
+                       if (caseConverted) {
+                               // Character has a conversion so copy that conversion in
+                               while (*caseConverted) {
+                                       converted[lenConverted++] = *caseConverted++;
+                                       if (lenConverted >= sizeConverted)
+                                               return 0;
+                               }
+                       } else {
+                               // Character has no conversion so copy the input to output
+                               for (size_t i=0; i<lenMixedChar; i++) {
+                                       converted[lenConverted++] = mixed[mixedPos+i];
+                                       if (lenConverted >= sizeConverted)
+                                               return 0;
+                               }
+                       }
+                       mixedPos += lenMixedChar;
+               }
+               return lenConverted;
+       }
+       void FinishedAdding() {
+               std::sort(characterToConversion.begin(), characterToConversion.end());
+               characters.reserve(characterToConversion.size());
+               conversions.reserve(characterToConversion.size());
+               for (CharacterToConversion::iterator it = characterToConversion.begin(); it != 
characterToConversion.end(); ++it) {
+                       characters.push_back(it->character);
+                       conversions.push_back(it->conversion);
+               }
+               // Empty the original calculated data completely
+               CharacterToConversion().swap(characterToConversion);
+       }
+};
+
+CaseConverter caseConvFold;
+CaseConverter caseConvUp;
+CaseConverter caseConvLow;
+
+void UTF8FromUTF32Character(int uch, char *putf) {
+       size_t k = 0;
+       if (uch < 0x80) {
+               putf[k++] = static_cast<char>(uch);
+       } else if (uch < 0x800) {
+               putf[k++] = static_cast<char>(0xC0 | (uch >> 6));
+               putf[k++] = static_cast<char>(0x80 | (uch & 0x3f));
+       } else if (uch < 0x10000) {
+               putf[k++] = static_cast<char>(0xE0 | (uch >> 12));
+               putf[k++] = static_cast<char>(0x80 | ((uch >> 6) & 0x3f));
+               putf[k++] = static_cast<char>(0x80 | (uch & 0x3f));
+       } else {
+               putf[k++] = static_cast<char>(0xF0 | (uch >> 18));
+               putf[k++] = static_cast<char>(0x80 | ((uch >> 12) & 0x3f));
+               putf[k++] = static_cast<char>(0x80 | ((uch >> 6) & 0x3f));
+               putf[k++] = static_cast<char>(0x80 | (uch & 0x3f));
+       }
+       putf[k] = 0;
+}
+
+void AddSymmetric(enum CaseConversion conversion, int lower,int upper) {
+       char lowerUTF8[UTF8MaxBytes+1];
+       UTF8FromUTF32Character(lower, lowerUTF8);
+       char upperUTF8[UTF8MaxBytes+1];
+       UTF8FromUTF32Character(upper, upperUTF8);
+
+       switch (conversion) {
+       case CaseConversionFold:
+               caseConvFold.Add(upper, lowerUTF8);
+               break;
+       case CaseConversionUpper:
+               caseConvUp.Add(lower, upperUTF8);
+               break;
+       case CaseConversionLower:
+               caseConvLow.Add(upper, lowerUTF8);
+               break;
+       }
+}
+
+void SetupConversions(enum CaseConversion conversion) {
+       // First initialize for the symmetric ranges
+       for (size_t i=0; i<sizeof(symmetricCaseConversionRanges)/sizeof(symmetricCaseConversionRanges[0]);) {
+               int lower = symmetricCaseConversionRanges[i++];
+               int upper = symmetricCaseConversionRanges[i++];
+               int length = symmetricCaseConversionRanges[i++];
+               int pitch = symmetricCaseConversionRanges[i++];
+               for (int j=0;j<length*pitch;j+=pitch) {
+                       AddSymmetric(conversion, lower+j, upper+j);
+               }
+       }
+       // Add the symmetric singletons
+       for (size_t i=0; i<sizeof(symmetricCaseConversions)/sizeof(symmetricCaseConversions[0]);) {
+               int lower = symmetricCaseConversions[i++];
+               int upper = symmetricCaseConversions[i++];
+               AddSymmetric(conversion, lower, upper);
+       }
+       // Add the complex cases
+       const char *sComplex = complexCaseConversions;
+       while (*sComplex) {
+               // Longest ligature is 3 character so 5 for safety
+               const size_t lenUTF8 = 5*UTF8MaxBytes+1;
+               char originUTF8[lenUTF8];
+               char foldedUTF8[lenUTF8];
+               char lowerUTF8[lenUTF8];
+               char upperUTF8[lenUTF8];
+               size_t i = 0;
+               while (*sComplex && *sComplex != '|') {
+                       originUTF8[i++] = *sComplex;
+                       sComplex++;
+               }
+               sComplex++;
+               originUTF8[i] = 0;
+               i = 0;
+               while (*sComplex && *sComplex != '|') {
+                       foldedUTF8[i++] = *sComplex;
+                       sComplex++;
+               }
+               sComplex++;
+               foldedUTF8[i] = 0;
+               i = 0;
+               while (*sComplex && *sComplex != '|') {
+                       upperUTF8[i++] = *sComplex;
+                       sComplex++;
+               }
+               sComplex++;
+               upperUTF8[i] = 0;
+               i = 0;
+               while (*sComplex && *sComplex != '|') {
+                       lowerUTF8[i++] = *sComplex;
+                       sComplex++;
+               }
+               sComplex++;
+               lowerUTF8[i] = 0;
+
+               int character = UnicodeFromUTF8(reinterpret_cast<unsigned char *>(originUTF8));
+
+               if (conversion == CaseConversionFold && foldedUTF8[0]) {
+                       caseConvFold.Add(character, foldedUTF8);
+               }
+
+               if (conversion == CaseConversionUpper && upperUTF8[0]) {
+                       caseConvUp.Add(character, upperUTF8);
+               }
+
+               if (conversion == CaseConversionLower && lowerUTF8[0]) {
+                       caseConvLow.Add(character, lowerUTF8);
+               }
+       }
+
+       switch (conversion) {
+       case CaseConversionFold:
+               caseConvFold.FinishedAdding();
+               break;
+       case CaseConversionUpper:
+               caseConvUp.FinishedAdding();
+               break;
+       case CaseConversionLower:
+               caseConvLow.FinishedAdding();
+               break;
+       }
+}
+
+CaseConverter *ConverterForConversion(enum CaseConversion conversion) {
+       switch (conversion) {
+       case CaseConversionFold:
+               return &caseConvFold;
+       case CaseConversionUpper:
+               return &caseConvUp;
+       case CaseConversionLower:
+               return &caseConvLow;
+       }
+       return 0;
+}
+
+}
+
+#ifdef SCI_NAMESPACE
+namespace Scintilla {
+#endif
+
+ICaseConverter *ConverterFor(enum CaseConversion conversion) {
+       CaseConverter *pCaseConv = ConverterForConversion(conversion);
+       if (!pCaseConv->Initialised())
+               SetupConversions(conversion);
+       return pCaseConv;
+}
+
+const char *CaseConvert(int character, enum CaseConversion conversion) {
+       CaseConverter *pCaseConv = ConverterForConversion(conversion);
+       if (!pCaseConv->Initialised())
+               SetupConversions(conversion);
+       return pCaseConv->Find(character);
+}
+
+size_t CaseConvertString(char *converted, size_t sizeConverted, const char *mixed, size_t lenMixed, enum 
CaseConversion conversion) {
+       CaseConverter *pCaseConv = ConverterForConversion(conversion);
+       if (!pCaseConv->Initialised())
+               SetupConversions(conversion);
+       return pCaseConv->CaseConvertString(converted, sizeConverted, mixed, lenMixed);
+}
+
+#ifdef SCI_NAMESPACE
+}
+#endif
diff --git a/plugins/scintilla/scintilla/src/CaseConvert.h b/plugins/scintilla/scintilla/src/CaseConvert.h
new file mode 100644
index 0000000..60de227
--- /dev/null
+++ b/plugins/scintilla/scintilla/src/CaseConvert.h
@@ -0,0 +1,47 @@
+// Scintilla source code edit control
+// Encoding: UTF-8
+/** @file CaseConvert.h
+ ** Performs Unicode case conversions.
+ ** Does not handle locale-sensitive case conversion.
+ **/
+// Copyright 2013 by Neil Hodgson <neilh scintilla org>
+// The License.txt file describes the conditions under which this software may be distributed.
+
+#ifndef CASECONVERT_H
+#define CASECONVERT_H
+
+#ifdef SCI_NAMESPACE
+namespace Scintilla {
+#endif
+
+enum CaseConversion {
+       CaseConversionFold,
+       CaseConversionUpper,
+       CaseConversionLower
+};
+
+class ICaseConverter {
+public:
+       virtual size_t CaseConvertString(char *converted, size_t sizeConverted, const char *mixed, size_t 
lenMixed) = 0;
+};
+
+ICaseConverter *ConverterFor(enum CaseConversion conversion);
+
+// Returns a UTF-8 string. Empty when no conversion
+const char *CaseConvert(int character, enum CaseConversion conversion);
+
+// When performing CaseConvertString, the converted value may be up to 3 times longer than the input.
+// Ligatures are often decomposed into multiple characters and long cases include:
+// ΐ "\xce\x90" folds to ΐ "\xce\xb9\xcc\x88\xcc\x81"
+const int maxExpansionCaseConversion=3;
+
+// Converts a mixed case string using a particular conversion.
+// Result may be a different length to input and the length is the return value.
+// If there is not enough space then 0 is returned.
+size_t CaseConvertString(char *converted, size_t sizeConverted, const char *mixed, size_t lenMixed, enum 
CaseConversion conversion);
+
+#ifdef SCI_NAMESPACE
+}
+#endif
+
+#endif
diff --git a/plugins/scintilla/scintilla/src/CaseFolder.cxx b/plugins/scintilla/scintilla/src/CaseFolder.cxx
new file mode 100644
index 0000000..44a94da
--- /dev/null
+++ b/plugins/scintilla/scintilla/src/CaseFolder.cxx
@@ -0,0 +1,68 @@
+// Scintilla source code edit control
+/** @file CaseFolder.cxx
+ ** Classes for case folding.
+ **/
+// Copyright 1998-2013 by Neil Hodgson <neilh scintilla org>
+// The License.txt file describes the conditions under which this software may be distributed.
+
+#include <vector>
+#include <algorithm>
+
+#include "CaseConvert.h"
+#include "UniConversion.h"
+#include "CaseFolder.h"
+
+#ifdef SCI_NAMESPACE
+using namespace Scintilla;
+#endif
+
+CaseFolder::~CaseFolder() {
+}
+
+CaseFolderTable::CaseFolderTable() {
+       for (size_t iChar=0; iChar<sizeof(mapping); iChar++) {
+               mapping[iChar] = static_cast<char>(iChar);
+       }
+}
+
+CaseFolderTable::~CaseFolderTable() {
+}
+
+size_t CaseFolderTable::Fold(char *folded, size_t sizeFolded, const char *mixed, size_t lenMixed) {
+       if (lenMixed > sizeFolded) {
+               return 0;
+       } else {
+               for (size_t i=0; i<lenMixed; i++) {
+                       folded[i] = mapping[static_cast<unsigned char>(mixed[i])];
+               }
+               return lenMixed;
+       }
+}
+
+void CaseFolderTable::SetTranslation(char ch, char chTranslation) {
+       mapping[static_cast<unsigned char>(ch)] = chTranslation;
+}
+
+void CaseFolderTable::StandardASCII() {
+       for (size_t iChar=0; iChar<sizeof(mapping); iChar++) {
+               if (iChar >= 'A' && iChar <= 'Z') {
+                       mapping[iChar] = static_cast<char>(iChar - 'A' + 'a');
+               } else {
+                       mapping[iChar] = static_cast<char>(iChar);
+               }
+       }
+}
+
+CaseFolderUnicode::CaseFolderUnicode() {
+       StandardASCII();
+       converter = ConverterFor(CaseConversionFold);
+}
+
+size_t CaseFolderUnicode::Fold(char *folded, size_t sizeFolded, const char *mixed, size_t lenMixed) {
+       if ((lenMixed == 1) && (sizeFolded > 0)) {
+               folded[0] = mapping[static_cast<unsigned char>(mixed[0])];
+               return 1;
+       } else {
+               return converter->CaseConvertString(folded, sizeFolded, mixed, lenMixed);
+       }
+}
diff --git a/plugins/scintilla/scintilla/src/CaseFolder.h b/plugins/scintilla/scintilla/src/CaseFolder.h
new file mode 100644
index 0000000..2d754d4
--- /dev/null
+++ b/plugins/scintilla/scintilla/src/CaseFolder.h
@@ -0,0 +1,45 @@
+// Scintilla source code edit control
+/** @file CaseFolder.h
+ ** Classes for case folding.
+ **/
+// Copyright 1998-2013 by Neil Hodgson <neilh scintilla org>
+// The License.txt file describes the conditions under which this software may be distributed.
+
+#ifndef CASEFOLDER_H
+#define CASEFOLDER_H
+
+#ifdef SCI_NAMESPACE
+namespace Scintilla {
+#endif
+
+class CaseFolder {
+public:
+       virtual ~CaseFolder();
+       virtual size_t Fold(char *folded, size_t sizeFolded, const char *mixed, size_t lenMixed) = 0;
+};
+
+class CaseFolderTable : public CaseFolder {
+protected:
+       char mapping[256];
+public:
+       CaseFolderTable();
+       virtual ~CaseFolderTable();
+       virtual size_t Fold(char *folded, size_t sizeFolded, const char *mixed, size_t lenMixed);
+       void SetTranslation(char ch, char chTranslation);
+       void StandardASCII();
+};
+
+class ICaseConverter;
+
+class CaseFolderUnicode : public CaseFolderTable {
+       ICaseConverter *converter;
+public:
+       CaseFolderUnicode();
+       virtual size_t Fold(char *folded, size_t sizeFolded, const char *mixed, size_t lenMixed);
+};
+
+#ifdef SCI_NAMESPACE
+}
+#endif
+
+#endif
diff --git a/plugins/scintilla/scintilla/src/Catalogue.cxx b/plugins/scintilla/scintilla/src/Catalogue.cxx
index cd69d81..1a56304 100644
--- a/plugins/scintilla/scintilla/src/Catalogue.cxx
+++ b/plugins/scintilla/scintilla/src/Catalogue.cxx
@@ -84,9 +84,9 @@ int Scintilla_LinkLexers() {
        LINK_LEXER(lmA68k);
        LINK_LEXER(lmAbaqus);
        LINK_LEXER(lmAda);
-       LINK_LEXER(lmAns1);
        LINK_LEXER(lmAPDL);
        LINK_LEXER(lmAsm);
+       LINK_LEXER(lmAsn1);
        LINK_LEXER(lmASY);
        LINK_LEXER(lmAU3);
        LINK_LEXER(lmAVE);
@@ -128,6 +128,7 @@ int Scintilla_LinkLexers() {
        LINK_LEXER(lmKix);
        LINK_LEXER(lmLatex);
        LINK_LEXER(lmLISP);
+       LINK_LEXER(lmLiterateHaskell);
        LINK_LEXER(lmLot);
        LINK_LEXER(lmLout);
        LINK_LEXER(lmLua);
@@ -171,6 +172,7 @@ int Scintilla_LinkLexers() {
        LINK_LEXER(lmSpecman);
        LINK_LEXER(lmSpice);
        LINK_LEXER(lmSQL);
+       LINK_LEXER(lmSTTXT);
        LINK_LEXER(lmTACL);
        LINK_LEXER(lmTADS3);
        LINK_LEXER(lmTAL);
diff --git a/plugins/scintilla/scintilla/src/CellBuffer.cxx b/plugins/scintilla/scintilla/src/CellBuffer.cxx
index 872616c..e88fd63 100644
--- a/plugins/scintilla/scintilla/src/CellBuffer.cxx
+++ b/plugins/scintilla/scintilla/src/CellBuffer.cxx
@@ -10,6 +10,8 @@
 #include <stdlib.h>
 #include <stdarg.h>
 
+#include <algorithm>
+
 #include "Platform.h"
 
 #include "Scintilla.h"
@@ -81,11 +83,15 @@ Action::~Action() {
        Destroy();
 }
 
-void Action::Create(actionType at_, int position_, char *data_, int lenData_, bool mayCoalesce_) {
+void Action::Create(actionType at_, int position_, const char *data_, int lenData_, bool mayCoalesce_) {
        delete []data;
+       data = NULL;
        position = position_;
        at = at_;
-       data = data_;
+       if (lenData_) {
+               data = new char[lenData_];
+               memcpy(data, data_, lenData_);
+       }
        lenData = lenData_;
        mayCoalesce = mayCoalesce_;
 }
@@ -162,7 +168,7 @@ void UndoHistory::EnsureUndoRoom() {
        }
 }
 
-void UndoHistory::AppendAction(actionType at, int position, char *data, int lengthData,
+const char *UndoHistory::AppendAction(actionType at, int position, const char *data, int lengthData,
        bool &startSequence, bool mayCoalesce) {
        EnsureUndoRoom();
        //Platform::DebugPrintf("%% %d action %d %d %d\n", at, position, lengthData, currentAction);
@@ -226,10 +232,12 @@ void UndoHistory::AppendAction(actionType at, int position, char *data, int leng
                currentAction++;
        }
        startSequence = oldCurrentAction != currentAction;
+       int actionWithData = currentAction;
        actions[currentAction].Create(at, position, data, lengthData, mayCoalesce);
        currentAction++;
        actions[currentAction].Create(startAction);
        maxAction = currentAction;
+       return actions[actionWithData].data;
 }
 
 void UndoHistory::BeginUndoAction() {
@@ -387,17 +395,13 @@ int CellBuffer::GapPosition() const {
 
 // The char* returned is to an allocation owned by the undo history
 const char *CellBuffer::InsertString(int position, const char *s, int insertLength, bool &startSequence) {
-       char *data = 0;
        // InsertString and DeleteChars are the bottleneck though which all changes occur
+       const char *data = s;
        if (!readOnly) {
                if (collectingUndo) {
                        // Save into the undo/redo stack, but only the characters - not the formatting
                        // This takes up about half load time
-                       data = new char[insertLength];
-                       for (int i = 0; i < insertLength; i++) {
-                               data[i] = s[i];
-                       }
-                       uh.AppendAction(insertAction, position, data, insertLength, startSequence);
+                       data = uh.AppendAction(insertAction, position, s, insertLength, startSequence);
                }
 
                BasicInsertString(position, s, insertLength);
@@ -435,15 +439,13 @@ bool CellBuffer::SetStyleFor(int position, int lengthStyle, char styleValue, cha
 const char *CellBuffer::DeleteChars(int position, int deleteLength, bool &startSequence) {
        // InsertString and DeleteChars are the bottleneck though which all changes occur
        PLATFORM_ASSERT(deleteLength > 0);
-       char *data = 0;
+       const char *data = 0;
        if (!readOnly) {
                if (collectingUndo) {
                        // Save into the undo/redo stack, but only the characters - not the formatting
-                       data = new char[deleteLength];
-                       for (int i = 0; i < deleteLength; i++) {
-                               data[i] = substance.ValueAt(position + i);
-                       }
-                       uh.AppendAction(removeAction, position, data, deleteLength, startSequence);
+                       // The gap would be moved to position anyway for the deletion so this doesn't cost 
extra
+                       data = substance.RangePointer(position, deleteLength);
+                       data = uh.AppendAction(removeAction, position, data, deleteLength, startSequence);
                }
 
                BasicDeleteChars(position, deleteLength);
@@ -496,7 +498,7 @@ void CellBuffer::SetSavePoint() {
        uh.SetSavePoint();
 }
 
-bool CellBuffer::IsSavePoint() {
+bool CellBuffer::IsSavePoint() const {
        return uh.IsSavePoint();
 }
 
@@ -728,7 +730,7 @@ void CellBuffer::DeleteUndoHistory() {
        uh.DeleteUndoHistory();
 }
 
-bool CellBuffer::CanUndo() {
+bool CellBuffer::CanUndo() const {
        return uh.CanUndo();
 }
 
@@ -750,7 +752,7 @@ void CellBuffer::PerformUndoStep() {
        uh.CompletedUndoStep();
 }
 
-bool CellBuffer::CanRedo() {
+bool CellBuffer::CanRedo() const {
        return uh.CanRedo();
 }
 
diff --git a/plugins/scintilla/scintilla/src/CellBuffer.h b/plugins/scintilla/scintilla/src/CellBuffer.h
index cde6f5a..82179ac 100644
--- a/plugins/scintilla/scintilla/src/CellBuffer.h
+++ b/plugins/scintilla/scintilla/src/CellBuffer.h
@@ -80,7 +80,7 @@ public:
 
        Action();
        ~Action();
-       void Create(actionType at_, int position_=0, char *data_=0, int lenData_=0, bool mayCoalesce_=true);
+       void Create(actionType at_, int position_=0, const char *data_=0, int lenData_=0, bool 
mayCoalesce_=true);
        void Destroy();
        void Grab(Action *source);
 };
@@ -105,7 +105,7 @@ public:
        UndoHistory();
        ~UndoHistory();
 
-       void AppendAction(actionType at, int position, char *data, int length, bool &startSequence, bool 
mayCoalesce=true);
+       const char *AppendAction(actionType at, int position, const char *data, int length, bool 
&startSequence, bool mayCoalesce=true);
 
        void BeginUndoAction();
        void EndUndoAction();
@@ -191,7 +191,7 @@ public:
        /// The save point is a marker in the undo stack where the container has stated that
        /// the buffer was saved. Undo and redo can move over the save point.
        void SetSavePoint();
-       bool IsSavePoint();
+       bool IsSavePoint() const;
 
        bool SetUndoCollection(bool collectUndo);
        bool IsCollectingUndo() const;
@@ -202,11 +202,11 @@ public:
 
        /// To perform an undo, StartUndo is called to retrieve the number of steps, then UndoStep is
        /// called that many times. Similarly for redo.
-       bool CanUndo();
+       bool CanUndo() const;
        int StartUndo();
        const Action &GetUndoStep() const;
        void PerformUndoStep();
-       bool CanRedo();
+       bool CanRedo() const;
        int StartRedo();
        const Action &GetRedoStep() const;
        void PerformRedoStep();
diff --git a/plugins/scintilla/scintilla/src/ContractionState.cxx 
b/plugins/scintilla/scintilla/src/ContractionState.cxx
index 957fd17..0636d90 100644
--- a/plugins/scintilla/scintilla/src/ContractionState.cxx
+++ b/plugins/scintilla/scintilla/src/ContractionState.cxx
@@ -7,6 +7,8 @@
 
 #include <string.h>
 
+#include <algorithm>
+
 #include "Platform.h"
 
 #include "SplitVector.h"
diff --git a/plugins/scintilla/scintilla/src/Decoration.cxx b/plugins/scintilla/scintilla/src/Decoration.cxx
index b489c3c..cda460a 100644
--- a/plugins/scintilla/scintilla/src/Decoration.cxx
+++ b/plugins/scintilla/scintilla/src/Decoration.cxx
@@ -9,6 +9,8 @@
 #include <stdlib.h>
 #include <stdarg.h>
 
+#include <algorithm>
+
 #include "Platform.h"
 
 #include "Scintilla.h"
@@ -27,7 +29,7 @@ Decoration::Decoration(int indicator_) : next(0), indicator(indicator_) {
 Decoration::~Decoration() {
 }
 
-bool Decoration::Empty() {
+bool Decoration::Empty() const {
        return (rs.Runs() == 1) && (rs.AllSameAs(0));
 }
 
@@ -157,7 +159,7 @@ void DecorationList::DeleteAnyEmpty() {
        }
 }
 
-int DecorationList::AllOnFor(int position) {
+int DecorationList::AllOnFor(int position) const {
        int mask = 0;
        for (Decoration *deco=root; deco; deco = deco->next) {
                if (deco->rs.ValueAt(position)) {
diff --git a/plugins/scintilla/scintilla/src/Decoration.h b/plugins/scintilla/scintilla/src/Decoration.h
index fedff97..23d70c7 100644
--- a/plugins/scintilla/scintilla/src/Decoration.h
+++ b/plugins/scintilla/scintilla/src/Decoration.h
@@ -20,7 +20,7 @@ public:
        Decoration(int indicator_);
        ~Decoration();
 
-       bool Empty();
+       bool Empty() const;
 };
 
 class DecorationList {
@@ -51,7 +51,7 @@ public:
        void InsertSpace(int position, int insertLength);
        void DeleteRange(int position, int deleteLength);
 
-       int AllOnFor(int position);
+       int AllOnFor(int position) const;
        int ValueAt(int indicator, int position);
        int Start(int indicator, int position);
        int End(int indicator, int position);
diff --git a/plugins/scintilla/scintilla/src/Document.cxx b/plugins/scintilla/scintilla/src/Document.cxx
index b75c754..0637c8d 100644
--- a/plugins/scintilla/scintilla/src/Document.cxx
+++ b/plugins/scintilla/scintilla/src/Document.cxx
@@ -13,6 +13,7 @@
 
 #include <string>
 #include <vector>
+#include <algorithm>
 
 #include "Platform.h"
 
@@ -27,6 +28,7 @@
 #include "CharClassify.h"
 #include "CharacterSet.h"
 #include "Decoration.h"
+#include "CaseFolder.h"
 #include "Document.h"
 #include "RESearch.h"
 #include "UniConversion.h"
@@ -102,8 +104,6 @@ Document::Document() {
        useTabs = true;
        tabIndents = true;
        backspaceUnindents = false;
-       watchers = 0;
-       lenWatchers = 0;
 
        matchesValid = false;
        regex = 0;
@@ -122,16 +122,13 @@ Document::Document() {
 }
 
 Document::~Document() {
-       for (int i = 0; i < lenWatchers; i++) {
-               watchers[i].watcher->NotifyDeleted(this, watchers[i].userData);
+       for (std::vector<WatcherWithUserData>::iterator it = watchers.begin(); it != watchers.end(); ++it) {
+               it->watcher->NotifyDeleted(this, it->userData);
        }
-       delete []watchers;
        for (int j=0; j<ldSize; j++) {
                delete perLineData[j];
                perLineData[j] = 0;
        }
-       watchers = 0;
-       lenWatchers = 0;
        delete regex;
        regex = 0;
        delete pli;
@@ -309,9 +306,9 @@ int SCI_METHOD Document::LineEnd(int line) const {
 }
 
 void SCI_METHOD Document::SetErrorStatus(int status) {
-       // Tell the watchers the lexer has changed.
-       for (int i = 0; i < lenWatchers; i++) {
-               watchers[i].watcher->NotifyErrorOccurred(this, watchers[i].userData, status);
+       // Tell the watchers an error has occurred.
+       for (std::vector<WatcherWithUserData>::iterator it = watchers.begin(); it != watchers.end(); ++it) {
+               it->watcher->NotifyErrorOccurred(this, it->userData, status);
        }
 }
 
@@ -396,7 +393,7 @@ int Document::GetLastChild(int lineParent, int level, int lastLine) {
        return lineMaxSubord;
 }
 
-int Document::GetFoldParent(int line) {
+int Document::GetFoldParent(int line) const {
        int level = GetLevel(line) & SC_FOLDLEVELNUMBERMASK;
        int lineLook = line - 1;
        while ((lineLook > 0) && (
@@ -420,7 +417,7 @@ void Document::GetHighlightDelimiters(HighlightDelimiter &highlightDelimiter, in
        int lookLine = line;
        int lookLineLevel = level;
        int lookLineLevelNum = lookLineLevel & SC_FOLDLEVELNUMBERMASK;
-       while ((lookLine > 0) && ((lookLineLevel & SC_FOLDLEVELWHITEFLAG) || 
+       while ((lookLine > 0) && ((lookLineLevel & SC_FOLDLEVELWHITEFLAG) ||
                ((lookLineLevel & SC_FOLDLEVELHEADERFLAG) && (lookLineLevelNum >= (GetLevel(lookLine + 1) & 
SC_FOLDLEVELNUMBERMASK))))) {
                lookLineLevel = GetLevel(--lookLine);
                lookLineLevelNum = lookLineLevel & SC_FOLDLEVELNUMBERMASK;
@@ -453,8 +450,8 @@ void Document::GetHighlightDelimiters(HighlightDelimiter &highlightDelimiter, in
                }
        }
        if (firstChangeableLineBefore == -1) {
-               for (lookLine = line - 1, lookLineLevel = GetLevel(lookLine), lookLineLevelNum = 
lookLineLevel & SC_FOLDLEVELNUMBERMASK; 
-                       lookLine >= beginFoldBlock; 
+               for (lookLine = line - 1, lookLineLevel = GetLevel(lookLine), lookLineLevelNum = 
lookLineLevel & SC_FOLDLEVELNUMBERMASK;
+                       lookLine >= beginFoldBlock;
                        lookLineLevel = GetLevel(--lookLine), lookLineLevelNum = lookLineLevel & 
SC_FOLDLEVELNUMBERMASK) {
                        if ((lookLineLevel & SC_FOLDLEVELWHITEFLAG) || (lookLineLevelNum > (level & 
SC_FOLDLEVELNUMBERMASK))) {
                                firstChangeableLineBefore = lookLine;
@@ -466,8 +463,8 @@ void Document::GetHighlightDelimiters(HighlightDelimiter &highlightDelimiter, in
                firstChangeableLineBefore = beginFoldBlock - 1;
 
        int firstChangeableLineAfter = -1;
-       for (lookLine = line + 1, lookLineLevel = GetLevel(lookLine), lookLineLevelNum = lookLineLevel & 
SC_FOLDLEVELNUMBERMASK; 
-               lookLine <= endFoldBlock; 
+       for (lookLine = line + 1, lookLineLevel = GetLevel(lookLine), lookLineLevelNum = lookLineLevel & 
SC_FOLDLEVELNUMBERMASK;
+               lookLine <= endFoldBlock;
                lookLineLevel = GetLevel(++lookLine), lookLineLevelNum = lookLineLevel & 
SC_FOLDLEVELNUMBERMASK) {
                if ((lookLineLevel & SC_FOLDLEVELHEADERFLAG) && (lookLineLevelNum < (GetLevel(lookLine + 1) & 
SC_FOLDLEVELNUMBERMASK))) {
                        firstChangeableLineAfter = lookLine;
@@ -483,11 +480,11 @@ void Document::GetHighlightDelimiters(HighlightDelimiter &highlightDelimiter, in
        highlightDelimiter.firstChangeableLineAfter = firstChangeableLineAfter;
 }
 
-int Document::ClampPositionIntoDocument(int pos) {
+int Document::ClampPositionIntoDocument(int pos) const {
        return Platform::Clamp(pos, 0, Length());
 }
 
-bool Document::IsCrLf(int pos) {
+bool Document::IsCrLf(int pos) const {
        if (pos < 0)
                return false;
        if (pos >= (Length() - 1))
@@ -692,7 +689,7 @@ int Document::NextPosition(int pos, int moveDir) const {
        return pos;
 }
 
-bool Document::NextCharacter(int &pos, int moveDir) {
+bool Document::NextCharacter(int &pos, int moveDir) const {
        // Returns true if pos changed
        int posNext = NextPosition(pos, moveDir);
        if (posNext == pos) {
@@ -703,6 +700,79 @@ bool Document::NextCharacter(int &pos, int moveDir) {
        }
 }
 
+static inline int UnicodeFromBytes(const unsigned char *us) {
+       if (us[0] < 0xC2) {
+               return us[0];
+       } else if (us[0] < 0xE0) {
+               return ((us[0] & 0x1F) << 6) + (us[1] & 0x3F);
+       } else if (us[0] < 0xF0) {
+               return ((us[0] & 0xF) << 12) + ((us[1] & 0x3F) << 6) + (us[2] & 0x3F);
+       } else if (us[0] < 0xF5) {
+               return ((us[0] & 0x7) << 18) + ((us[1] & 0x3F) << 12) + ((us[2] & 0x3F) << 6) + (us[3] & 
0x3F);
+       }
+       return us[0];
+}
+
+// Return -1  on out-of-bounds
+int SCI_METHOD Document::GetRelativePosition(int positionStart, int characterOffset) const {
+       int pos = positionStart;
+       if (dbcsCodePage) {
+               const int increment = (characterOffset > 0) ? 1 : -1;
+               while (characterOffset != 0) {
+                       const int posNext = NextPosition(pos, increment);
+                       if (posNext == pos)
+                               return INVALID_POSITION;
+                       pos = posNext;
+                       characterOffset -= increment;
+               }
+       } else {
+               pos = positionStart + characterOffset;
+               if ((pos < 0) || (pos > Length()))
+                       return INVALID_POSITION;
+       }
+       return pos;
+}
+
+int SCI_METHOD Document::GetCharacterAndWidth(int position, int *pWidth) const {
+       int character;
+       int bytesInCharacter = 1;
+       if (dbcsCodePage) {
+               const unsigned char leadByte = static_cast<unsigned char>(cb.CharAt(position));
+               if (SC_CP_UTF8 == dbcsCodePage) {
+                       if (UTF8IsAscii(leadByte)) {
+                               // Single byte character or invalid
+                               character =  leadByte;
+                       } else {
+                               const int widthCharBytes = UTF8BytesOfLead[leadByte];
+                               unsigned char charBytes[UTF8MaxBytes] = {leadByte,0,0,0};
+                               for (int b=1; b<widthCharBytes; b++)
+                                       charBytes[b] = static_cast<unsigned char>(cb.CharAt(position+b));
+                               int utf8status = UTF8Classify(charBytes, widthCharBytes);
+                               if (utf8status & UTF8MaskInvalid) {
+                                       // Report as singleton surrogate values which are invalid Unicode
+                                       character =  0xDC80 + leadByte;
+                               } else {
+                                       bytesInCharacter = utf8status & UTF8MaskWidth;
+                                       character = UnicodeFromBytes(charBytes);
+                               }
+                       }
+               } else {
+                       if (IsDBCSLeadByte(leadByte)) {
+                               bytesInCharacter = 2;
+                               character = (leadByte << 8) | static_cast<unsigned 
char>(cb.CharAt(position+1));
+                       } else {
+                               character = leadByte;
+                       }
+               }
+       } else {
+               character = cb.CharAt(position);
+       }
+       if (pWidth) {
+               *pWidth = bytesInCharacter;
+       }
+       return character;
+}
+
 int SCI_METHOD Document::CodePage() const {
        return dbcsCodePage;
 }
@@ -715,7 +785,7 @@ bool SCI_METHOD Document::IsDBCSLeadByte(char ch) const {
                        // Shift_jis
                        return ((uch >= 0x81) && (uch <= 0x9F)) ||
                                ((uch >= 0xE0) && (uch <= 0xFC));
-                               // Lead bytes F0 to FC may be a Microsoft addition. 
+                               // Lead bytes F0 to FC may be a Microsoft addition.
                case 936:
                        // GBK
                        return (uch >= 0x81) && (uch <= 0xFE);
@@ -750,7 +820,7 @@ static inline bool IsSpaceOrTab(int ch) {
 //   2) Break before punctuation
 //   3) Break after whole character
 
-int Document::SafeSegment(const char *text, int length, int lengthSegment) {
+int Document::SafeSegment(const char *text, int length, int lengthSegment) const {
        if (length <= lengthSegment)
                return length;
        int lastSpaceBreak = -1;
@@ -892,7 +962,7 @@ void * SCI_METHOD Document::ConvertToDocument() {
 int Document::Undo() {
        int newPos = -1;
        CheckReadOnly();
-       if (enteredModification == 0) {
+       if ((enteredModification == 0) && (cb.IsCollectingUndo())) {
                enteredModification++;
                if (!cb.IsReadOnly()) {
                        bool startSavePoint = cb.IsSavePoint();
@@ -977,7 +1047,7 @@ int Document::Undo() {
 int Document::Redo() {
        int newPos = -1;
        CheckReadOnly();
-       if (enteredModification == 0) {
+       if ((enteredModification == 0) && (cb.IsCollectingUndo())) {
                enteredModification++;
                if (!cb.IsReadOnly()) {
                        bool startSavePoint = cb.IsSavePoint();
@@ -1050,11 +1120,6 @@ bool Document::InsertCString(int position, const char *s) {
        return InsertString(position, s, static_cast<int>(s ? strlen(s) : 0));
 }
 
-void Document::ChangeChar(int pos, char ch) {
-       DeleteChars(pos, 1);
-       InsertChar(pos, ch);
-}
-
 void Document::DelChar(int pos) {
        DeleteChars(pos, LenChar(pos));
 }
@@ -1212,32 +1277,25 @@ void Document::Indent(bool forwards, int lineBottom, int lineTop) {
 
 // Convert line endings for a piece of text to a particular mode.
 // Stop at len or when a NUL is found.
-// Caller must delete the returned pointer.
-char *Document::TransformLineEnds(int *pLenOut, const char *s, size_t len, int eolModeWanted) {
-       char *dest = new char[2 * len + 1];
-       const char *sptr = s;
-       char *dptr = dest;
-       for (size_t i = 0; (i < len) && (*sptr != '\0'); i++) {
-               if (*sptr == '\n' || *sptr == '\r') {
+std::string Document::TransformLineEnds(const char *s, size_t len, int eolModeWanted) {
+       std::string dest;
+       for (size_t i = 0; (i < len) && (s[i]); i++) {
+               if (s[i] == '\n' || s[i] == '\r') {
                        if (eolModeWanted == SC_EOL_CR) {
-                               *dptr++ = '\r';
+                               dest.push_back('\r');
                        } else if (eolModeWanted == SC_EOL_LF) {
-                               *dptr++ = '\n';
+                               dest.push_back('\n');
                        } else { // eolModeWanted == SC_EOL_CRLF
-                               *dptr++ = '\r';
-                               *dptr++ = '\n';
+                               dest.push_back('\r');
+                               dest.push_back('\n');
                        }
-                       if ((*sptr == '\r') && (i+1 < len) && (*(sptr+1) == '\n')) {
+                       if ((s[i] == '\r') && (i+1 < len) && (s[i+1] == '\n')) {
                                i++;
-                               sptr++;
                        }
-                       sptr++;
                } else {
-                       *dptr++ = *sptr++;
+                       dest.push_back(s[i]);
                }
        }
-       *dptr++ = '\0';
-       *pLenOut = (dptr - dest) - 1;
        return dest;
 }
 
@@ -1291,7 +1349,7 @@ bool Document::IsWhiteLine(int line) const {
        return true;
 }
 
-int Document::ParaUp(int pos) {
+int Document::ParaUp(int pos) const {
        int line = LineFromPosition(pos);
        line--;
        while (line >= 0 && IsWhiteLine(line)) { // skip empty lines
@@ -1304,7 +1362,7 @@ int Document::ParaUp(int pos) {
        return LineStart(line);
 }
 
-int Document::ParaDown(int pos) {
+int Document::ParaDown(int pos) const {
        int line = LineFromPosition(pos);
        while (line < LinesTotal() && !IsWhiteLine(line)) { // skip non-empty lines
                line++;
@@ -1318,7 +1376,7 @@ int Document::ParaDown(int pos) {
                return LineEnd(line-1);
 }
 
-CharClassify::cc Document::WordCharClass(unsigned char ch) {
+CharClassify::cc Document::WordCharClass(unsigned char ch) const {
        if ((SC_CP_UTF8 == dbcsCodePage) && (!UTF8IsAscii(ch)))
                return CharClassify::ccWord;
        return charClass.GetClass(ch);
@@ -1409,7 +1467,7 @@ int Document::NextWordEnd(int pos, int delta) {
  * Check that the character at the given position is a word or punctuation character and that
  * the previous character is of a different character class.
  */
-bool Document::IsWordStartAt(int pos) {
+bool Document::IsWordStartAt(int pos) const {
        if (pos > 0) {
                CharClassify::cc ccPos = WordCharClass(CharAt(pos));
                return (ccPos == CharClassify::ccWord || ccPos == CharClassify::ccPunctuation) &&
@@ -1422,7 +1480,7 @@ bool Document::IsWordStartAt(int pos) {
  * Check that the character at the given position is a word or punctuation character and that
  * the next character is of a different character class.
  */
-bool Document::IsWordEndAt(int pos) {
+bool Document::IsWordEndAt(int pos) const {
        if (pos < Length()) {
                CharClassify::cc ccPrev = WordCharClass(CharAt(pos-1));
                return (ccPrev == CharClassify::ccWord || ccPrev == CharClassify::ccPunctuation) &&
@@ -1435,52 +1493,11 @@ bool Document::IsWordEndAt(int pos) {
  * Check that the given range is has transitions between character classes at both
  * ends and where the characters on the inside are word or punctuation characters.
  */
-bool Document::IsWordAt(int start, int end) {
+bool Document::IsWordAt(int start, int end) const {
        return IsWordStartAt(start) && IsWordEndAt(end);
 }
 
-static inline char MakeLowerCase(char ch) {
-       if (ch < 'A' || ch > 'Z')
-               return ch;
-       else
-               return static_cast<char>(ch - 'A' + 'a');
-}
-
-CaseFolderTable::CaseFolderTable() {
-       for (size_t iChar=0; iChar<sizeof(mapping); iChar++) {
-               mapping[iChar] = static_cast<char>(iChar);
-       }
-}
-
-CaseFolderTable::~CaseFolderTable() {
-}
-
-size_t CaseFolderTable::Fold(char *folded, size_t sizeFolded, const char *mixed, size_t lenMixed) {
-       if (lenMixed > sizeFolded) {
-               return 0;
-       } else {
-               for (size_t i=0; i<lenMixed; i++) {
-                       folded[i] = mapping[static_cast<unsigned char>(mixed[i])];
-               }
-               return lenMixed;
-       }
-}
-
-void CaseFolderTable::SetTranslation(char ch, char chTranslation) {
-       mapping[static_cast<unsigned char>(ch)] = chTranslation;
-}
-
-void CaseFolderTable::StandardASCII() {
-       for (size_t iChar=0; iChar<sizeof(mapping); iChar++) {
-               if (iChar >= 'A' && iChar <= 'Z') {
-                       mapping[iChar] = static_cast<char>(iChar - 'A' + 'a');
-               } else {
-                       mapping[iChar] = static_cast<char>(iChar);
-               }
-       }
-}
-
-bool Document::MatchesWordOptions(bool word, bool wordStart, int pos, int length) {
+bool Document::MatchesWordOptions(bool word, bool wordStart, int pos, int length) const {
        return (!word && !wordStart) ||
                        (word && IsWordAt(pos, pos + length)) ||
                        (wordStart && IsWordStartAt(pos));
@@ -1667,25 +1684,6 @@ int Document::LinesTotal() const {
        return cb.Lines();
 }
 
-void Document::ChangeCase(Range r, bool makeUpperCase) {
-       for (int pos = r.start; pos < r.end;) {
-               int len = LenChar(pos);
-               if (len == 1) {
-                       char ch = CharAt(pos);
-                       if (makeUpperCase) {
-                               if (IsLowerCase(ch)) {
-                                       ChangeChar(pos, static_cast<char>(MakeUpperCase(ch)));
-                               }
-                       } else {
-                               if (IsUpperCase(ch)) {
-                                       ChangeChar(pos, static_cast<char>(MakeLowerCase(ch)));
-                               }
-                       }
-               }
-               pos += len;
-       }
-}
-
 void Document::SetDefaultCharClasses(bool includeWordClass) {
     charClass.SetDefaultCharClasses(includeWordClass);
 }
@@ -1763,8 +1761,9 @@ void Document::EnsureStyledTo(int pos) {
                        pli->Colourise(endStyledTo, pos);
                } else {
                        // Ask the watchers to style, and stop as soon as one responds.
-                       for (int i = 0; pos > GetEndStyled() && i < lenWatchers; i++) {
-                               watchers[i].watcher->NotifyStyleNeeded(this, watchers[i].userData, pos);
+                       for (std::vector<WatcherWithUserData>::iterator it = watchers.begin();
+                               (pos > GetEndStyled()) && (it != watchers.end()); ++it) {
+                               it->watcher->NotifyStyleNeeded(this, it->userData, pos);
                        }
                }
        }
@@ -1772,8 +1771,8 @@ void Document::EnsureStyledTo(int pos) {
 
 void Document::LexerChanged() {
        // Tell the watchers the lexer has changed.
-       for (int i = 0; i < lenWatchers; i++) {
-               watchers[i].watcher->NotifyLexerChanged(this, watchers[i].userData);
+       for (std::vector<WatcherWithUserData>::iterator it = watchers.begin(); it != watchers.end(); ++it) {
+               it->watcher->NotifyLexerChanged(this, it->userData);
        }
 }
 
@@ -1799,7 +1798,7 @@ void SCI_METHOD Document::ChangeLexerState(int start, int end) {
        NotifyModified(mh);
 }
 
-StyledText Document::MarginStyledText(int line) {
+StyledText Document::MarginStyledText(int line) const {
        LineAnnotation *pla = static_cast<LineAnnotation *>(perLineData[ldMargin]);
        return StyledText(pla->Length(line), pla->Text(line),
                pla->MultipleStyles(line), pla->Style(line), pla->Styles(line));
@@ -1821,10 +1820,6 @@ void Document::MarginSetStyles(int line, const unsigned char *styles) {
        NotifyModified(DocModification(SC_MOD_CHANGEMARGIN, LineStart(line), 0, 0, 0, line));
 }
 
-int Document::MarginLength(int line) const {
-       return static_cast<LineAnnotation *>(perLineData[ldMargin])->Length(line);
-}
-
 void Document::MarginClearAll() {
        int maxEditorLine = LinesTotal();
        for (int l=0; l<maxEditorLine; l++)
@@ -1833,11 +1828,7 @@ void Document::MarginClearAll() {
        static_cast<LineAnnotation *>(perLineData[ldMargin])->ClearAll();
 }
 
-bool Document::AnnotationAny() const {
-       return static_cast<LineAnnotation *>(perLineData[ldAnnotation])->AnySet();
-}
-
-StyledText Document::AnnotationStyledText(int line) {
+StyledText Document::AnnotationStyledText(int line) const {
        LineAnnotation *pla = static_cast<LineAnnotation *>(perLineData[ldAnnotation]);
        return StyledText(pla->Length(line), pla->Text(line),
                pla->MultipleStyles(line), pla->Style(line), pla->Styles(line));
@@ -1866,10 +1857,6 @@ void Document::AnnotationSetStyles(int line, const unsigned char *styles) {
        }
 }
 
-int Document::AnnotationLength(int line) const {
-       return static_cast<LineAnnotation *>(perLineData[ldAnnotation])->Length(line);
-}
-
 int Document::AnnotationLines(int line) const {
        return static_cast<LineAnnotation *>(perLineData[ldAnnotation])->Lines(line);
 }
@@ -1895,54 +1882,34 @@ void SCI_METHOD Document::DecorationFillRange(int position, int value, int fillL
 }
 
 bool Document::AddWatcher(DocWatcher *watcher, void *userData) {
-       for (int i = 0; i < lenWatchers; i++) {
-               if ((watchers[i].watcher == watcher) &&
-                       (watchers[i].userData == userData))
-                       return false;
-       }
-       WatcherWithUserData *pwNew = new WatcherWithUserData[lenWatchers + 1];
-       for (int j = 0; j < lenWatchers; j++)
-               pwNew[j] = watchers[j];
-       pwNew[lenWatchers].watcher = watcher;
-       pwNew[lenWatchers].userData = userData;
-       delete []watchers;
-       watchers = pwNew;
-       lenWatchers++;
+       WatcherWithUserData wwud(watcher, userData);
+       std::vector<WatcherWithUserData>::iterator it = 
+               std::find(watchers.begin(), watchers.end(), wwud);
+       if (it != watchers.end())
+               return false;
+       watchers.push_back(wwud);
        return true;
 }
 
 bool Document::RemoveWatcher(DocWatcher *watcher, void *userData) {
-       for (int i = 0; i < lenWatchers; i++) {
-               if ((watchers[i].watcher == watcher) &&
-                       (watchers[i].userData == userData)) {
-                       if (lenWatchers == 1) {
-                               delete []watchers;
-                               watchers = 0;
-                               lenWatchers = 0;
-                       } else {
-                               WatcherWithUserData *pwNew = new WatcherWithUserData[lenWatchers];
-                               for (int j = 0; j < lenWatchers - 1; j++) {
-                                       pwNew[j] = (j < i) ? watchers[j] : watchers[j + 1];
-                               }
-                               delete []watchers;
-                               watchers = pwNew;
-                               lenWatchers--;
-                       }
-                       return true;
-               }
+       std::vector<WatcherWithUserData>::iterator it = 
+               std::find(watchers.begin(), watchers.end(), WatcherWithUserData(watcher, userData));
+       if (it != watchers.end()) {
+               watchers.erase(it);
+               return true;
        }
        return false;
 }
 
 void Document::NotifyModifyAttempt() {
-       for (int i = 0; i < lenWatchers; i++) {
-               watchers[i].watcher->NotifyModifyAttempt(this, watchers[i].userData);
+       for (std::vector<WatcherWithUserData>::iterator it = watchers.begin(); it != watchers.end(); ++it) {
+               it->watcher->NotifyModifyAttempt(this, it->userData);
        }
 }
 
 void Document::NotifySavePoint(bool atSavePoint) {
-       for (int i = 0; i < lenWatchers; i++) {
-               watchers[i].watcher->NotifySavePoint(this, watchers[i].userData, atSavePoint);
+       for (std::vector<WatcherWithUserData>::iterator it = watchers.begin(); it != watchers.end(); ++it) {
+               it->watcher->NotifySavePoint(this, it->userData, atSavePoint);
        }
 }
 
@@ -1952,12 +1919,12 @@ void Document::NotifyModified(DocModification mh) {
        } else if (mh.modificationType & SC_MOD_DELETETEXT) {
                decorations.DeleteRange(mh.position, mh.length);
        }
-       for (int i = 0; i < lenWatchers; i++) {
-               watchers[i].watcher->NotifyModified(this, mh, watchers[i].userData);
+       for (std::vector<WatcherWithUserData>::iterator it = watchers.begin(); it != watchers.end(); ++it) {
+               it->watcher->NotifyModified(this, mh, it->userData);
        }
 }
 
-bool Document::IsWordPartSeparator(char ch) {
+bool Document::IsWordPartSeparator(char ch) const {
        return (WordCharClass(ch) == CharClassify::ccWord) && IsPunctuation(ch);
 }
 
@@ -2127,10 +2094,9 @@ int Document::BraceMatch(int position, int /*maxReStyle*/) {
  */
 class BuiltinRegex : public RegexSearchBase {
 public:
-       BuiltinRegex(CharClassify *charClassTable) : search(charClassTable), substituted(NULL) {}
+       BuiltinRegex(CharClassify *charClassTable) : search(charClassTable) {}
 
        virtual ~BuiltinRegex() {
-               delete substituted;
        }
 
        virtual long FindText(Document *doc, int minPos, int maxPos, const char *s,
@@ -2141,7 +2107,7 @@ public:
 
 private:
        RESearch search;
-       char *substituted;
+       std::string substituted;
 };
 
 // Define a way for the Regular Expression code to access the document
@@ -2236,6 +2202,8 @@ long BuiltinRegex::FindText(Document *doc, int minPos, int maxPos, const char *s
                int success = search.Execute(di, startOfLine, endOfLine);
                if (success) {
                        pos = search.bopat[0];
+                       // Ensure only whole characters selected
+                       search.eopat[0] = doc->MovePositionOutsideChar(search.eopat[0], 1, false);
                        lenRet = search.eopat[0] - search.bopat[0];
                        // There can be only one start of a line, so no need to look for last match in line
                        if ((increment == -1) && (s[0] != '^')) {
@@ -2261,86 +2229,55 @@ long BuiltinRegex::FindText(Document *doc, int minPos, int maxPos, const char *s
 }
 
 const char *BuiltinRegex::SubstituteByPosition(Document *doc, const char *text, int *length) {
-       delete []substituted;
-       substituted = 0;
+       substituted.clear();
        DocumentIndexer di(doc, doc->Length());
-       if (!search.GrabMatches(di))
-               return 0;
-       unsigned int lenResult = 0;
-       for (int i = 0; i < *length; i++) {
-               if (text[i] == '\\') {
-                       if (text[i + 1] >= '0' && text[i + 1] <= '9') {
-                               unsigned int patNum = text[i + 1] - '0';
-                               lenResult += search.eopat[patNum] - search.bopat[patNum];
-                               i++;
-                       } else {
-                               switch (text[i + 1]) {
-                               case 'a':
-                               case 'b':
-                               case 'f':
-                               case 'n':
-                               case 'r':
-                               case 't':
-                               case 'v':
-                               case '\\':
-                                       i++;
-                               }
-                               lenResult++;
-                       }
-               } else {
-                       lenResult++;
-               }
-       }
-       substituted = new char[lenResult + 1];
-       char *o = substituted;
+       search.GrabMatches(di);
        for (int j = 0; j < *length; j++) {
                if (text[j] == '\\') {
                        if (text[j + 1] >= '0' && text[j + 1] <= '9') {
                                unsigned int patNum = text[j + 1] - '0';
                                unsigned int len = search.eopat[patNum] - search.bopat[patNum];
-                               if (search.pat[patNum]) // Will be null if try for a match that did not occur
-                                       memcpy(o, search.pat[patNum], len);
-                               o += len;
+                               if (!search.pat[patNum].empty())        // Will be null if try for a match 
that did not occur
+                                       substituted.append(search.pat[patNum].c_str(), len);
                                j++;
                        } else {
                                j++;
                                switch (text[j]) {
                                case 'a':
-                                       *o++ = '\a';
+                                       substituted.push_back('\a');
                                        break;
                                case 'b':
-                                       *o++ = '\b';
+                                       substituted.push_back('\b');
                                        break;
                                case 'f':
-                                       *o++ = '\f';
+                                       substituted.push_back('\f');
                                        break;
                                case 'n':
-                                       *o++ = '\n';
+                                       substituted.push_back('\n');
                                        break;
                                case 'r':
-                                       *o++ = '\r';
+                                       substituted.push_back('\r');
                                        break;
                                case 't':
-                                       *o++ = '\t';
+                                       substituted.push_back('\t');
                                        break;
                                case 'v':
-                                       *o++ = '\v';
+                                       substituted.push_back('\v');
                                        break;
                                case '\\':
-                                       *o++ = '\\';
+                                       substituted.push_back('\\');
                                        break;
                                default:
-                                       *o++ = '\\';
+                                       substituted.push_back('\\');
                                        j--;
                                }
                        }
                } else {
-                       *o++ = text[j];
+                       substituted.push_back(text[j]);
                }
        }
-       *o = '\0';
-       *length = lenResult;
-       return substituted;
+       *length = static_cast<int>(substituted.length());
+       return substituted.c_str();
 }
 
 #ifndef SCI_OWNREGEX
diff --git a/plugins/scintilla/scintilla/src/Document.h b/plugins/scintilla/scintilla/src/Document.h
index 16804d3..5147875 100644
--- a/plugins/scintilla/scintilla/src/Document.h
+++ b/plugins/scintilla/scintilla/src/Document.h
@@ -128,23 +128,23 @@ public:
                firstChangeableLineAfter = -1;
        }
 
-       bool NeedsDrawing(int line) {
+       bool NeedsDrawing(int line) const {
                return isEnabled && (line <= firstChangeableLineBefore || line >= firstChangeableLineAfter);
        }
 
-       bool IsFoldBlockHighlighted(int line) {
+       bool IsFoldBlockHighlighted(int line) const {
                return isEnabled && beginFoldBlock != -1 && beginFoldBlock <= line && line <= endFoldBlock;
        }
 
-       bool IsHeadOfFoldBlock(int line) {
+       bool IsHeadOfFoldBlock(int line) const {
                return beginFoldBlock == line && line < endFoldBlock;
        }
 
-       bool IsBodyOfFoldBlock(int line) {
+       bool IsBodyOfFoldBlock(int line) const {
                return beginFoldBlock != -1 && beginFoldBlock < line && line < endFoldBlock;
        }
 
-       bool IsTailOfFoldBlock(int line) {
+       bool IsTailOfFoldBlock(int line) const {
                return beginFoldBlock != -1 && beginFoldBlock < line && line == endFoldBlock;
        }
 
@@ -155,24 +155,6 @@ public:
        bool isEnabled;
 };
 
-class CaseFolder {
-public:
-       virtual ~CaseFolder() {
-       }
-       virtual size_t Fold(char *folded, size_t sizeFolded, const char *mixed, size_t lenMixed) = 0;
-};
-
-class CaseFolderTable : public CaseFolder {
-protected:
-       char mapping[256];
-public:
-       CaseFolderTable();
-       virtual ~CaseFolderTable();
-       virtual size_t Fold(char *folded, size_t sizeFolded, const char *mixed, size_t lenMixed);
-       void SetTranslation(char ch, char chTranslation);
-       void StandardASCII();
-};
-
 class Document;
 
 class LexInterface {
@@ -198,17 +180,17 @@ class Document : PerLine, public IDocumentWithLineEnd, public ILoader {
 
 public:
        /** Used to pair watcher pointer with user data. */
-       class WatcherWithUserData {
-       public:
+       struct WatcherWithUserData {
                DocWatcher *watcher;
                void *userData;
-               WatcherWithUserData() {
-                       watcher = 0;
-                       userData = 0;
+               WatcherWithUserData(DocWatcher *watcher_=0, void *userData_=0) :
+                       watcher(watcher_), userData(userData_) {
+               }
+               bool operator==(const WatcherWithUserData &other) const {
+                       return (watcher == other.watcher) && (userData == other.userData);
                }
        };
 
-       enum charClassification { ccSpace, ccNewLine, ccWord, ccPunctuation };
 private:
        int refCount;
        CellBuffer cb;
@@ -221,8 +203,7 @@ private:
        int enteredStyling;
        int enteredReadOnlyCount;
 
-       WatcherWithUserData *watchers;
-       int lenWatchers;
+       std::vector<WatcherWithUserData> watchers;
 
        // ldSize is not real data - it is for dimensions and loops
        enum lineData { ldMarkers, ldLevels, ldState, ldMargin, ldAnnotation, ldSize };
@@ -260,9 +241,9 @@ public:
        virtual void Init();
        int LineEndTypesSupported() const;
        bool SetDBCSCodePage(int dbcsCodePage_);
-       int GetLineEndTypesAllowed() { return cb.GetLineEndTypes(); }
+       int GetLineEndTypesAllowed() const { return cb.GetLineEndTypes(); }
        bool SetLineEndTypesAllowed(int lineEndBitSet_);
-       int GetLineEndTypesActive() { return cb.GetLineEndTypes(); }
+       int GetLineEndTypesActive() const { return cb.GetLineEndTypes(); }
        virtual void InsertLine(int line);
        virtual void RemoveLine(int line);
 
@@ -273,16 +254,18 @@ public:
        void SCI_METHOD SetErrorStatus(int status);
 
        int SCI_METHOD LineFromPosition(int pos) const;
-       int ClampPositionIntoDocument(int pos);
-       bool IsCrLf(int pos);
+       int ClampPositionIntoDocument(int pos) const;
+       bool IsCrLf(int pos) const;
        int LenChar(int pos);
        bool InGoodUTF8(int pos, int &start, int &end) const;
        int MovePositionOutsideChar(int pos, int moveDir, bool checkLineEnd=true);
        int NextPosition(int pos, int moveDir) const;
-       bool NextCharacter(int &pos, int moveDir);      // Returns true if pos changed
+       bool NextCharacter(int &pos, int moveDir) const;        // Returns true if pos changed
+       int SCI_METHOD GetRelativePosition(int positionStart, int characterOffset) const;
+       int SCI_METHOD GetCharacterAndWidth(int position, int *pWidth) const;
        int SCI_METHOD CodePage() const;
        bool SCI_METHOD IsDBCSLeadByte(char ch) const;
-       int SafeSegment(const char *text, int length, int lengthSegment);
+       int SafeSegment(const char *text, int length, int lengthSegment) const;
 
        // Gateways to modifying document
        void ModifiedAt(int pos);
@@ -293,18 +276,18 @@ public:
        void * SCI_METHOD ConvertToDocument();
        int Undo();
        int Redo();
-       bool CanUndo() { return cb.CanUndo(); }
-       bool CanRedo() { return cb.CanRedo(); }
+       bool CanUndo() const { return cb.CanUndo(); }
+       bool CanRedo() const { return cb.CanRedo(); }
        void DeleteUndoHistory() { cb.DeleteUndoHistory(); }
        bool SetUndoCollection(bool collectUndo) {
                return cb.SetUndoCollection(collectUndo);
        }
-       bool IsCollectingUndo() { return cb.IsCollectingUndo(); }
+       bool IsCollectingUndo() const { return cb.IsCollectingUndo(); }
        void BeginUndoAction() { cb.BeginUndoAction(); }
        void EndUndoAction() { cb.EndUndoAction(); }
        void AddUndoAction(int token, bool mayCoalesce) { cb.AddUndoAction(token, mayCoalesce); }
        void SetSavePoint();
-       bool IsSavePoint() { return cb.IsSavePoint(); }
+       bool IsSavePoint() const { return cb.IsSavePoint(); }
        const char * SCI_METHOD BufferPointer() { return cb.BufferPointer(); }
        const char *RangePointer(int position, int rangeLength) { return cb.RangePointer(position, 
rangeLength); }
        int GapPosition() const { return cb.GapPosition(); }
@@ -316,18 +299,17 @@ public:
        int CountCharacters(int startPos, int endPos);
        int FindColumn(int line, int column);
        void Indent(bool forwards, int lineBottom, int lineTop);
-       static char *TransformLineEnds(int *pLenOut, const char *s, size_t len, int eolModeWanted);
+       static std::string TransformLineEnds(const char *s, size_t len, int eolModeWanted);
        void ConvertLineEnds(int eolModeSet);
        void SetReadOnly(bool set) { cb.SetReadOnly(set); }
-       bool IsReadOnly() { return cb.IsReadOnly(); }
+       bool IsReadOnly() const { return cb.IsReadOnly(); }
 
        bool InsertChar(int pos, char ch);
        bool InsertCString(int position, const char *s);
-       void ChangeChar(int pos, char ch);
        void DelChar(int pos);
        void DelCharBack(int pos);
 
-       char CharAt(int position) { return cb.CharAt(position); }
+       char CharAt(int position) const { return cb.CharAt(position); }
        void SCI_METHOD GetCharRange(char *buffer, int position, int lengthRetrieve) const {
                cb.GetCharRange(buffer, position, lengthRetrieve);
        }
@@ -354,7 +336,7 @@ public:
        int SCI_METHOD GetLevel(int line) const;
        void ClearLevels();
        int GetLastChild(int lineParent, int level=-1, int lastLine=-1);
-       int GetFoldParent(int line);
+       int GetFoldParent(int line) const;
        void GetHighlightDelimiters(HighlightDelimiter &hDelimiter, int line, int lastLine);
 
        void Indent(bool forwards);
@@ -363,7 +345,7 @@ public:
        int NextWordEnd(int pos, int delta);
        int SCI_METHOD Length() const { return cb.Length(); }
        void Allocate(int newSize) { cb.Allocate(newSize); }
-       bool MatchesWordOptions(bool word, bool wordStart, int pos, int length);
+       bool MatchesWordOptions(bool word, bool wordStart, int pos, int length) const;
        bool HasCaseFolder(void) const;
        void SetCaseFolder(CaseFolder *pcf_);
        long FindText(int minPos, int maxPos, const char *search, bool caseSensitive, bool word,
@@ -371,8 +353,6 @@ public:
        const char *SubstituteByPosition(const char *text, int *length);
        int LinesTotal() const;
 
-       void ChangeCase(Range r, bool makeUpperCase);
-
        void SetDefaultCharClasses(bool includeWordClass);
        void SetCharClasses(const unsigned char *chars, CharClassify::cc newCharClass);
        int GetCharsOfClass(CharClassify::cc charClass, unsigned char *buffer);
@@ -380,10 +360,10 @@ public:
        void SCI_METHOD StartStyling(int position, char mask);
        bool SCI_METHOD SetStyleFor(int length, char style);
        bool SCI_METHOD SetStyles(int length, const char *styles);
-       int GetEndStyled() { return endStyled; }
+       int GetEndStyled() const { return endStyled; }
        void EnsureStyledTo(int pos);
        void LexerChanged();
-       int GetStyleClock() { return styleClock; }
+       int GetStyleClock() const { return styleClock; }
        void IncrementStyleClock();
        void SCI_METHOD DecorationSetCurrentIndicator(int indicator) {
                decorations.SetCurrentIndicator(indicator);
@@ -395,42 +375,37 @@ public:
        int GetMaxLineState();
        void SCI_METHOD ChangeLexerState(int start, int end);
 
-       StyledText MarginStyledText(int line);
+       StyledText MarginStyledText(int line) const;
        void MarginSetStyle(int line, int style);
        void MarginSetStyles(int line, const unsigned char *styles);
        void MarginSetText(int line, const char *text);
-       int MarginLength(int line) const;
        void MarginClearAll();
 
-       bool AnnotationAny() const;
-       StyledText AnnotationStyledText(int line);
+       StyledText AnnotationStyledText(int line) const;
        void AnnotationSetText(int line, const char *text);
        void AnnotationSetStyle(int line, int style);
        void AnnotationSetStyles(int line, const unsigned char *styles);
-       int AnnotationLength(int line) const;
        int AnnotationLines(int line) const;
        void AnnotationClearAll();
 
        bool AddWatcher(DocWatcher *watcher, void *userData);
        bool RemoveWatcher(DocWatcher *watcher, void *userData);
-       const WatcherWithUserData *GetWatchers() const { return watchers; }
-       int GetLenWatchers() const { return lenWatchers; }
 
-       CharClassify::cc WordCharClass(unsigned char ch);
-       bool IsWordPartSeparator(char ch);
+       CharClassify::cc WordCharClass(unsigned char ch) const;
+       bool IsWordPartSeparator(char ch) const;
        int WordPartLeft(int pos);
        int WordPartRight(int pos);
        int ExtendStyleRange(int pos, int delta, bool singleLine = false);
        bool IsWhiteLine(int line) const;
-       int ParaUp(int pos);
-       int ParaDown(int pos);
-       int IndentSize() { return actualIndentInChars; }
+       int ParaUp(int pos) const;
+       int ParaDown(int pos) const;
+       int IndentSize() const { return actualIndentInChars; }
        int BraceMatch(int position, int maxReStyle);
 
 private:
-       bool IsWordStartAt(int pos);
-       bool IsWordEndAt(int pos);
-       bool IsWordAt(int start, int end);
+       bool IsWordStartAt(int pos) const;
+       bool IsWordEndAt(int pos) const;
+       bool IsWordAt(int start, int end) const;
 
        void NotifyModifyAttempt();
        void NotifySavePoint(bool atSavePoint);
diff --git a/plugins/scintilla/scintilla/src/Editor.cxx b/plugins/scintilla/scintilla/src/Editor.cxx
index d02f095..acb840f 100644
--- a/plugins/scintilla/scintilla/src/Editor.cxx
+++ b/plugins/scintilla/scintilla/src/Editor.cxx
@@ -36,6 +36,7 @@
 #include "ViewStyle.h"
 #include "CharClassify.h"
 #include "Decoration.h"
+#include "CaseFolder.h"
 #include "Document.h"
 #include "UniConversion.h"
 #include "Selection.h"
@@ -106,7 +107,7 @@ Editor::Editor() {
        stylesValid = false;
        technology = SC_TECHNOLOGY_DEFAULT;
        scaleRGBAImage = 100;
-       
+
        printMagnification = 0;
        printColourMode = SC_PRINT_NORMAL;
        printWrapState = eWrapWord;
@@ -116,6 +117,7 @@ Editor::Editor() {
        hasFocus = false;
        hideSelection = false;
        inOverstrike = false;
+       drawOverstrikeCaret = true;
        errorStatus = 0;
        mouseDownCaptures = true;
 
@@ -149,7 +151,7 @@ Editor::Editor() {
 
        caretYPolicy = CARET_EVEN;
        caretYSlop = 0;
-       
+
        visiblePolicy = 0;
        visibleSlop = 0;
 
@@ -208,11 +210,10 @@ Editor::Editor() {
 
        recordingMacro = false;
        foldFlags = 0;
+       foldAutomatic = 0;
 
        wrapState = eWrapNone;
        wrapWidth = LineLayout::wrapWidthInfinite;
-       wrapStart = wrapLineLarge;
-       wrapEnd = wrapLineLarge;
        wrapVisualFlags = 0;
        wrapVisualFlagsLocation = 0;
        wrapVisualStartIndent = 0;
@@ -332,7 +333,7 @@ Point Editor::DocumentPointFromView(Point ptView) {
        return ptDocument;
 }
 
-int Editor::TopLineOfMain() {
+int Editor::TopLineOfMain() const {
        if (wMargin.GetID())
                return 0;
        else
@@ -488,7 +489,7 @@ int Editor::XFromPosition(SelectionPosition sp) {
        return pt.x - vs.textStart + xOffset;
 }
 
-int Editor::LineFromLocation(Point pt) {
+int Editor::LineFromLocation(Point pt) const {
        return cs.DocFromDisplay(pt.y / vs.lineHeight + topLine);
 }
 
@@ -721,11 +722,11 @@ void Editor::InvalidateRange(int start, int end) {
        RedrawRect(RectangleFromRange(start, end));
 }
 
-int Editor::CurrentPosition() {
+int Editor::CurrentPosition() const {
        return sel.MainCaret();
 }
 
-bool Editor::SelectionEmpty() {
+bool Editor::SelectionEmpty() const {
        return sel.Empty();
 }
 
@@ -960,8 +961,8 @@ int Editor::MovePositionTo(SelectionPosition newPos, Selection::selTypes selt, b
        int currentLine = pdoc->LineFromPosition(newPos.Position());
        if (ensureVisible) {
                // In case in need of wrapping to ensure DisplayFromDoc works.
-               if (currentLine >= wrapStart)
-                       WrapLines(true, -1);
+               if (currentLine >= wrapPending.start)
+                       WrapLines(wsAll);
                XYScrollPosition newXY = XYScrollToMakeVisible(
                        SelectionRange(posDrag.IsValid() ? posDrag : sel.RangeMain().caret), xysDefault);
                if (simpleCaret && (newXY.xOffset == xOffset)) {
@@ -1136,7 +1137,7 @@ void Editor::MoveSelectedLines(int lineDelta) {
                pdoc->InsertCString(pdoc->Length(), eol);
        GoToLine(currentLine + lineDelta);
 
-       pdoc->InsertCString(CurrentPosition(), selectedText.s);
+       pdoc->InsertCString(CurrentPosition(), selectedText.Data());
        if (appendEol) {
                pdoc->InsertCString(CurrentPosition() + selectionLength, eol);
                selectionLength += istrlen(eol);
@@ -1240,10 +1241,15 @@ Editor::XYScrollPosition Editor::XYScrollToMakeVisible(const SelectionRange rang
        Point ptAnchor = LocationFromPosition(range.anchor);
        const Point ptOrigin = GetVisibleOriginInMain();
        pt.x += ptOrigin.x;
+       pt.y += ptOrigin.y;
        ptAnchor.x += ptOrigin.x;
+       ptAnchor.y += ptOrigin.y;
        const Point ptBottomCaret(pt.x, pt.y + vs.lineHeight - 1);
 
        XYScrollPosition newXY(xOffset, topLine);
+       if (rcClient.Empty()) {
+               return newXY;
+       }
 
        // Vertical positioning
        if ((options & xysVertical) && (pt.y < rcClient.top || ptBottomCaret.y >= rcClient.bottom || 
(caretYPolicy & CARET_STRICT) != 0)) {
@@ -1535,17 +1541,12 @@ void Editor::UpdateSystemCaret() {
 }
 
 void Editor::NeedWrapping(int docLineStart, int docLineEnd) {
-       docLineStart = Platform::Clamp(docLineStart, 0, pdoc->LinesTotal());
-       if (wrapStart > docLineStart) {
-               wrapStart = docLineStart;
+//Platform::DebugPrintf("\nNeedWrapping: %0d..%0d\n", docLineStart, docLineEnd);
+       if (wrapPending.AddRange(docLineStart, docLineEnd)) {
                llc.Invalidate(LineLayout::llPositions);
        }
-       if (wrapEnd < docLineEnd) {
-               wrapEnd = docLineEnd;
-       }
-       wrapEnd = Platform::Clamp(wrapEnd, 0, pdoc->LinesTotal());
        // Wrap lines during idle.
-       if ((wrapState != eWrapNone) && (wrapEnd != wrapStart)) {
+       if ((wrapState != eWrapNone) && wrapPending.NeedsWrap()) {
                SetIdle(true);
        }
 }
@@ -1561,117 +1562,97 @@ bool Editor::WrapOneLine(Surface *surface, int lineToWrap) {
                (vs.annotationVisible ? pdoc->AnnotationLines(lineToWrap) : 0));
 }
 
-// Check if wrapping needed and perform any needed wrapping.
-// fullwrap: if true, all lines which need wrapping will be done,
-//           in this single call.
-// priorityWrapLineStart: If greater than or equal to zero, all lines starting from
-//           here to 1 page + 100 lines past will be wrapped (even if there are
-//           more lines under wrapping process in idle).
-// If it is neither fullwrap, nor priorityWrap, then 1 page + 100 lines will be
-// wrapped, if there are any wrapping going on in idle. (Generally this
-// condition is called only from idler).
+// Perform  wrapping for a subset of the lines needing wrapping.
+// wsAll: wrap all lines which need wrapping in this single call
+// wsVisible: wrap currently visible lines
+// wsIdle: wrap one page + 100 lines
 // Return true if wrapping occurred.
-bool Editor::WrapLines(bool fullWrap, int priorityWrapLineStart) {
-       // If there are any pending wraps, do them during idle if possible.
-       int linesInOneCall = LinesOnScreen() + 100;
-       if (priorityWrapLineStart >= 0) {
-               // Using DocFromDisplay() here may result in chicken and egg problem in certain corner cases,
-               // which will hopefully be handled by added 100 lines. If some lines are still missed, idle 
wrapping will catch on.
-               int docLinesInOneCall = cs.DocFromDisplay(topLine + LinesOnScreen() + 100) - 
cs.DocFromDisplay(topLine);
-               linesInOneCall = Platform::Maximum(linesInOneCall, docLinesInOneCall);
-       }
-       if (wrapState != eWrapNone) {
-               if (wrapStart < wrapEnd) {
-                       if (!SetIdle(true)) {
-                               // Idle processing not supported so full wrap required.
-                               fullWrap = true;
-                       }
-               }
-               if (!fullWrap && priorityWrapLineStart >= 0 &&
-                       // .. and if the paint window is outside pending wraps
-                       (((priorityWrapLineStart + linesInOneCall) < wrapStart) ||
-                        (priorityWrapLineStart > wrapEnd))) {
-                       // No priority wrap pending
-                       return false;
-               }
-       }
+bool Editor::WrapLines(enum wrapScope ws) {
        int goodTopLine = topLine;
        bool wrapOccurred = false;
-       if (wrapStart <= pdoc->LinesTotal()) {
-               if (wrapState == eWrapNone) {
-                       if (wrapWidth != LineLayout::wrapWidthInfinite) {
-                               wrapWidth = LineLayout::wrapWidthInfinite;
-                               for (int lineDoc = 0; lineDoc < pdoc->LinesTotal(); lineDoc++) {
-                                       cs.SetHeight(lineDoc, 1 +
-                                               (vs.annotationVisible ? pdoc->AnnotationLines(lineDoc) : 0));
-                               }
-                               wrapOccurred = true;
+       if (wrapState == eWrapNone) {
+               if (wrapWidth != LineLayout::wrapWidthInfinite) {
+                       wrapWidth = LineLayout::wrapWidthInfinite;
+                       for (int lineDoc = 0; lineDoc < pdoc->LinesTotal(); lineDoc++) {
+                               cs.SetHeight(lineDoc, 1 +
+                                       (vs.annotationVisible ? pdoc->AnnotationLines(lineDoc) : 0));
+                       }
+                       wrapOccurred = true;
+               }
+               wrapPending.Reset();
+
+       } else if (wrapPending.NeedsWrap()) {
+               wrapPending.start = std::min(wrapPending.start, pdoc->LinesTotal());
+               if (!SetIdle(true)) {
+                       // Idle processing not supported so full wrap required.
+                       ws = wsAll;
+               }
+               // Decide where to start wrapping
+               int lineToWrap = wrapPending.start;
+               int lineToWrapEnd = std::min(wrapPending.end, pdoc->LinesTotal());
+               const int lineDocTop = cs.DocFromDisplay(topLine);
+               const int subLineTop = topLine - cs.DisplayFromDoc(lineDocTop);
+               if (ws == wsVisible) {
+                       lineToWrap = Platform::Clamp(lineDocTop-5, wrapPending.start, pdoc->LinesTotal());
+                       // Priority wrap to just after visible area.
+                       // Since wrapping could reduce display lines, treat each
+                       // as taking only one display line.
+                       lineToWrapEnd = lineDocTop;
+                       int lines = LinesOnScreen() + 1;
+                       while ((lineToWrapEnd < cs.LinesInDoc()) && (lines>0)) {
+                               if (cs.GetVisible(lineToWrapEnd))
+                                       lines--;
+                               lineToWrapEnd++;
+                       }
+                       // .. and if the paint window is outside pending wraps
+                       if ((lineToWrap > wrapPending.end) || (lineToWrapEnd < wrapPending.start)) {
+                               // Currently visible text does not need wrapping
+                               return false;
                        }
-                       wrapStart = wrapLineLarge;
-                       wrapEnd = wrapLineLarge;
-               } else {
-                       if (wrapEnd >= pdoc->LinesTotal())
-                               wrapEnd = pdoc->LinesTotal();
-                       //ElapsedTime et;
-                       int lineDocTop = cs.DocFromDisplay(topLine);
-                       int subLineTop = topLine - cs.DisplayFromDoc(lineDocTop);
+               } else if (ws == wsIdle) {
+                       lineToWrapEnd = lineToWrap + LinesOnScreen() + 100;
+               }
+               const int lineEndNeedWrap = std::min(wrapPending.end, pdoc->LinesTotal());
+               lineToWrapEnd = std::min(lineToWrapEnd, lineEndNeedWrap);
+
+               // Ensure all lines being wrapped are styled.
+               pdoc->EnsureStyledTo(pdoc->LineStart(lineToWrapEnd));
+
+               if (lineToWrap < lineToWrapEnd) {
+
                        PRectangle rcTextArea = GetClientRectangle();
                        rcTextArea.left = vs.textStart;
-                       rcTextArea.right -= vs.textStart;
+                       rcTextArea.right -= vs.rightMarginWidth;
                        wrapWidth = rcTextArea.Width();
                        RefreshStyleData();
                        AutoSurface surface(this);
                        if (surface) {
-                               bool priorityWrap = false;
-                               int lastLineToWrap = wrapEnd;
-                               int lineToWrap = wrapStart;
-                               if (!fullWrap) {
-                                       if (priorityWrapLineStart >= 0) {
-                                               // This is a priority wrap.
-                                               lineToWrap = priorityWrapLineStart;
-                                               lastLineToWrap = priorityWrapLineStart + linesInOneCall;
-                                               priorityWrap = true;
-                                       } else {
-                                               // This is idle wrap.
-                                               lastLineToWrap = wrapStart + linesInOneCall;
-                                       }
-                                       if (lastLineToWrap >= wrapEnd)
-                                               lastLineToWrap = wrapEnd;
-                               } // else do a fullWrap.
+//Platform::DebugPrintf("Wraplines: scope=%0d need=%0d..%0d perform=%0d..%0d\n", ws, wrapPending.start, 
wrapPending.end, lineToWrap, lineToWrapEnd);
 
-                               // Ensure all lines being wrapped are styled.
-                               pdoc->EnsureStyledTo(pdoc->LineEnd(lastLineToWrap));
-
-                               // Platform::DebugPrintf("Wraplines: full = %d, priorityStart = %d (wrapping: 
%d to %d)\n", fullWrap, priorityWrapLineStart, lineToWrap, lastLineToWrap);
-                               // Platform::DebugPrintf("Pending wraps: %d to %d\n", wrapStart, wrapEnd);
-                               while (lineToWrap < lastLineToWrap) {
+                               while (lineToWrap < lineToWrapEnd) {
                                        if (WrapOneLine(surface, lineToWrap)) {
                                                wrapOccurred = true;
                                        }
+                                       wrapPending.Wrapped(lineToWrap);
                                        lineToWrap++;
                                }
-                               if (!priorityWrap)
-                                       wrapStart = lineToWrap;
-                               // If wrapping is done, bring it to resting position
-                               if (wrapStart >= wrapEnd) {
-                                       wrapStart = wrapLineLarge;
-                                       wrapEnd = wrapLineLarge;
-                               }
+
+                               goodTopLine = cs.DisplayFromDoc(lineDocTop) + std::min(subLineTop, 
cs.GetHeight(lineDocTop)-1);
                        }
-                       goodTopLine = cs.DisplayFromDoc(lineDocTop);
-                       if (subLineTop < cs.GetHeight(lineDocTop))
-                               goodTopLine += subLineTop;
-                       else
-                               goodTopLine += cs.GetHeight(lineDocTop);
-                       //double durWrap = et.Duration(true);
-                       //Platform::DebugPrintf("Wrap:%9.6g \n", durWrap);
+               }
+
+               // If wrapping is done, bring it to resting position
+               if (wrapPending.start >= lineEndNeedWrap) {
+                       wrapPending.Reset();
                }
        }
+
        if (wrapOccurred) {
                SetScrollBars();
                SetTopLine(Platform::Clamp(goodTopLine, 0, MaxScrollPos()));
                SetVerticalScrollPos();
        }
+
        return wrapOccurred;
 }
 
@@ -1734,7 +1715,7 @@ void Editor::LinesSplit(int pixelWidth) {
        }
 }
 
-int Editor::SubstituteMarkerIfEmpty(int markerCheck, int markerDefault) {
+int Editor::SubstituteMarkerIfEmpty(int markerCheck, int markerDefault) const {
        if (vs.markers[markerCheck].markType == SC_MARK_EMPTY)
                return markerDefault;
        return markerCheck;
@@ -1762,7 +1743,7 @@ static int WidthStyledText(Surface *surface, ViewStyle &vs, int styleOffset,
                size_t endSegment = start;
                while ((endSegment+1 < len) && (static_cast<size_t>(styles[endSegment+1]) == style))
                        endSegment++;
-               width += surface->WidthText(vs.styles[style+styleOffset].font, text + start, 
+               width += surface->WidthText(vs.styles[style+styleOffset].font, text + start,
                        static_cast<int>(endSegment - start + 1));
                start = endSegment + 1;
        }
@@ -1827,6 +1808,8 @@ void Editor::PaintSelMargin(Surface *surfWindow, PRectangle &rc) {
        if (vs.fixedColumnWidth == 0)
                return;
 
+       AllocateGraphics();
+       RefreshStyleData();
        RefreshPixMaps(surfWindow);
 
        PRectangle rcMargin = GetClientRectangle();
@@ -2284,7 +2267,7 @@ void Editor::LayoutLine(int line, Surface *surface, ViewStyle &vstyle, LineLayou
                                if (vstyle.styles[ll->styles[charInLine]].visible) {
                                        if (isControl) {
                                                if (ll->chars[charInLine] == '\t') {
-                                                       ll->positions[charInLine + 1] = 
+                                                       ll->positions[charInLine + 1] =
                                                                ((static_cast<int>((startsegx + 2) / 
tabWidth) + 1) * tabWidth) - startsegx;
                                                } else if (controlCharSymbol < 32) {
                                                        if (ctrlCharWidth[ll->chars[charInLine]] == 0) {
@@ -2420,14 +2403,14 @@ void Editor::LayoutLine(int line, Surface *surface, ViewStyle &vstyle, LineLayou
        }
 }
 
-ColourDesired Editor::SelectionBackground(ViewStyle &vsDraw, bool main) {
+ColourDesired Editor::SelectionBackground(ViewStyle &vsDraw, bool main) const {
        return main ?
                (primarySelection ? vsDraw.selbackground : vsDraw.selbackground2) :
                vsDraw.selAdditionalBackground;
 }
 
 ColourDesired Editor::TextBackground(ViewStyle &vsDraw, bool overrideBackground,
-        ColourDesired background, int inSelection, bool inHotspot, int styleMain, int i, LineLayout *ll) {
+        ColourDesired background, int inSelection, bool inHotspot, int styleMain, int i, LineLayout *ll) 
const {
        if (inSelection == 1) {
                if (vsDraw.selbackset && (vsDraw.selAlpha == SC_ALPHA_NOALPHA)) {
                        return SelectionBackground(vsDraw, true);
@@ -3495,7 +3478,7 @@ void Editor::DrawCarets(Surface *surface, ViewStyle &vsDraw, int lineDoc, int xS
                                        /* Dragging text, use a line caret */
                                        rcCaret.left = xposCaret - caretWidthOffset;
                                        rcCaret.right = rcCaret.left + vsDraw.caretWidth;
-                               } else if (inOverstrike) {
+                               } else if (inOverstrike && drawOverstrikeCaret) {
                                        /* Overstrike (insert mode), use a modified bar caret */
                                        rcCaret.top = rcCaret.bottom - 2;
                                        rcCaret.left = xposCaret + 1;
@@ -3537,6 +3520,8 @@ void Editor::Paint(Surface *surfaceWindow, PRectangle rcArea) {
                return; // Scroll bars may have changed so need redraw
        RefreshPixMaps(surfaceWindow);
 
+       paintAbandonedByStyling = false;
+
        StyleToPositionInView(PositionAfterArea(rcArea));
 
        PRectangle rcClient = GetClientRectangle();
@@ -3552,19 +3537,13 @@ void Editor::Paint(Surface *surfaceWindow, PRectangle rcArea) {
                ypos += screenLinePaintFirst * vs.lineHeight;
        int yposScreen = screenLinePaintFirst * vs.lineHeight;
 
-       bool paintAbandonedByStyling = paintState == paintAbandoned;
        if (NotifyUpdateUI()) {
                RefreshStyleData();
                RefreshPixMaps(surfaceWindow);
        }
 
-       // Call priority lines wrap on a window of lines which are likely
-       // to rendered with the following paint (that is wrap the visible
-       //      lines first).
-       int startLineToWrap = cs.DocFromDisplay(topLine) - 5;
-       if (startLineToWrap < 0)
-               startLineToWrap = 0;
-       if (WrapLines(false, startLineToWrap)) {
+       // Wrap the visible lines if needed.
+       if (WrapLines(wsVisible)) {
                // The wrapping process has changed the height of some lines so
                // abandon this paint for a complete repaint.
                if (AbandonPaint()) {
@@ -3848,7 +3827,7 @@ long Editor::FormatRange(bool draw, Sci_RangeToFormat *pfr) {
        vsPrint.braceBadLightIndicatorSet = false;
 
        // Set colours for printing according to users settings
-       for (size_t sty = 0; sty < vsPrint.stylesSize; sty++) {
+       for (size_t sty = 0; sty < vsPrint.styles.size(); sty++) {
                if (printColourMode == SC_PRINT_INVERTLIGHT) {
                        vsPrint.styles[sty].fore = InvertedLight(vsPrint.styles[sty].fore);
                        vsPrint.styles[sty].back = InvertedLight(vsPrint.styles[sty].back);
@@ -4141,7 +4120,7 @@ void Editor::AddCharUTF(char *s, unsigned int len, bool treatAsDBCS) {
        if (treatAsDBCS) {
                NotifyChar((static_cast<unsigned char>(s[0]) << 8) |
                        static_cast<unsigned char>(s[1]));
-       } else {
+       } else if (len > 0) {
                int byte = static_cast<unsigned char>(s[0]);
                if ((byte < 0xC0) || (1 == len)) {
                        // Handles UTF-8 characters between 0x01 and 0x7F and single byte
@@ -4441,7 +4420,7 @@ void Editor::DelCharBack(bool allowLineStartDeletion) {
 void Editor::NotifyFocus(bool) {}
 
 void Editor::SetCtrlID(int identifier) {
-       ctrlID = identifier; 
+       ctrlID = identifier;
 }
 
 void Editor::NotifyStyleToNeeded(int endStyleNeeded) {
@@ -4561,11 +4540,32 @@ bool Editor::NotifyMarginClick(Point pt, bool shift, bool ctrl, bool alt) {
                x += vs.ms[margin].width;
        }
        if ((marginClicked >= 0) && vs.ms[marginClicked].sensitive) {
+               int position = pdoc->LineStart(LineFromLocation(pt));
+               if ((vs.ms[marginClicked].mask & SC_MASK_FOLDERS) && (foldAutomatic & 
SC_AUTOMATICFOLD_CLICK)) {
+                       int lineClick = pdoc->LineFromPosition(position);
+                       if (shift && ctrl) {
+                               FoldAll(SC_FOLDACTION_TOGGLE);
+                       } else {
+                               int levelClick = pdoc->GetLevel(lineClick);
+                               if (levelClick & SC_FOLDLEVELHEADERFLAG) {
+                                       if (shift) {
+                                               // Ensure all children visible
+                                               FoldExpand(lineClick, SC_FOLDACTION_EXPAND, levelClick);
+                                       } else if (ctrl) {
+                                               FoldExpand(lineClick, SC_FOLDACTION_TOGGLE, levelClick);
+                                       } else {
+                                               // Toggle this line
+                                               FoldLine(lineClick, SC_FOLDACTION_TOGGLE);
+                                       }
+                               }
+                       }
+                       return true;
+               }
                SCNotification scn = {0};
                scn.nmhdr.code = SCN_MARGINCLICK;
                scn.modifiers = (shift ? SCI_SHIFT : 0) | (ctrl ? SCI_CTRL : 0) |
                        (alt ? SCI_ALT : 0);
-               scn.position = pdoc->LineStart(LineFromLocation(pt));
+               scn.position = position;
                scn.margin = marginClicked;
                NotifyParent(scn);
                return true;
@@ -4704,17 +4704,19 @@ void Editor::NotifyModified(Document *, DocModification mh, void *) {
                                                insertingNewLine = true;
                                }
                                if (insertingNewLine && (mh.position != pdoc->LineStart(lineOfPos)))
-                                       NotifyNeedShown(mh.position, pdoc->LineStart(lineOfPos+1) - 
mh.position);
+                                       NeedShown(mh.position, pdoc->LineStart(lineOfPos+1) - mh.position);
                                else
-                                       NotifyNeedShown(mh.position, 0);
+                                       NeedShown(mh.position, 0);
                        } else if (mh.modificationType & SC_MOD_BEFOREDELETE) {
-                               NotifyNeedShown(mh.position, mh.length);
+                               NeedShown(mh.position, mh.length);
                        }
                }
                if (mh.linesAdded != 0) {
                        // Update contraction state for inserted and removed lines
                        // lineOfPos should be calculated in context of state before modification, shouldn't 
it
                        int lineOfPos = pdoc->LineFromPosition(mh.position);
+                       if (mh.position > pdoc->LineStart(lineOfPos))
+                               lineOfPos++;    // Affecting subsequent lines
                        if (mh.linesAdded > 0) {
                                cs.InsertLines(lineOfPos, mh.linesAdded);
                        } else {
@@ -4765,6 +4767,9 @@ void Editor::NotifyModified(Document *, DocModification mh, void *) {
                        }
                }
        }
+       if ((mh.modificationType & SC_MOD_CHANGEFOLD) && (foldAutomatic & SC_AUTOMATICFOLD_CHANGE)) {
+               FoldChanged(mh.line, mh.foldLevelNow, mh.foldLevelPrev);
+       }
 
        // NOW pay the piper WRT "deferred" visual updates
        if (IsLastStep(mh)) {
@@ -4987,10 +4992,9 @@ void Editor::ChangeCaseOfSelection(int caseMapping) {
                SelectionRange current = sel.Range(r);
                SelectionRange currentNoVS = current;
                currentNoVS.ClearVirtualSpace();
-               char *text = CopyRange(currentNoVS.Start().Position(), currentNoVS.End().Position());
                size_t rangeBytes = currentNoVS.Length();
                if (rangeBytes > 0) {
-                       std::string sText(text, rangeBytes);
+                       std::string sText = RangeText(currentNoVS.Start().Position(), 
currentNoVS.End().Position());
 
                        std::string sMapped = CaseMapString(sText, caseMapping);
 
@@ -4998,22 +5002,31 @@ void Editor::ChangeCaseOfSelection(int caseMapping) {
                                size_t firstDifference = 0;
                                while (sMapped[firstDifference] == sText[firstDifference])
                                        firstDifference++;
-                               size_t lastDifference = sMapped.size() - 1;
-                               while (sMapped[lastDifference] == sText[lastDifference])
-                                       lastDifference--;
-                               size_t endSame = sMapped.size() - 1 - lastDifference;
+                               size_t lastDifferenceText = sText.size() - 1;
+                               size_t lastDifferenceMapped = sMapped.size() - 1;
+                               while (sMapped[lastDifferenceMapped] == sText[lastDifferenceText]) {
+                                       lastDifferenceText--;
+                                       lastDifferenceMapped--;
+                               }
+                               size_t endDifferenceText = sText.size() - 1 - lastDifferenceText;
                                pdoc->DeleteChars(
                                        static_cast<int>(currentNoVS.Start().Position() + firstDifference),
-                                       static_cast<int>(rangeBytes - firstDifference - endSame));
+                                       static_cast<int>(rangeBytes - firstDifference - endDifferenceText));
                                pdoc->InsertString(
                                        static_cast<int>(currentNoVS.Start().Position() + firstDifference),
                                        sMapped.c_str() + firstDifference,
-                                       static_cast<int>(lastDifference - firstDifference + 1));
+                                       static_cast<int>(lastDifferenceMapped - firstDifference + 1));
                                // Automatic movement changes selection so reset to exactly the same as it 
was.
+                               int diffSizes = static_cast<int>(sMapped.size() - sText.size());
+                               if (diffSizes != 0) {
+                                       if (current.anchor > current.caret)
+                                               current.anchor.Add(diffSizes);
+                                       else
+                                               current.caret.Add(diffSizes);
+                               }
                                sel.Range(r) = current;
                        }
                }
-               delete []text;
        }
 }
 
@@ -5025,17 +5038,15 @@ void Editor::LineTranspose() {
                int endPrev = pdoc->LineEnd(line - 1);
                int start = pdoc->LineStart(line);
                int end = pdoc->LineEnd(line);
-               char *line1 = CopyRange(startPrev, endPrev);
+               std::string line1 = RangeText(startPrev, endPrev);
                int len1 = endPrev - startPrev;
-               char *line2 = CopyRange(start, end);
+               std::string line2 = RangeText(start, end);
                int len2 = end - start;
                pdoc->DeleteChars(start, len2);
                pdoc->DeleteChars(startPrev, len1);
-               pdoc->InsertString(startPrev, line2, len2);
-               pdoc->InsertString(start - len1 + len2, line1, len1);
+               pdoc->InsertString(startPrev, line2.c_str(), len2);
+               pdoc->InsertString(start - len1 + len2, line1.c_str(), len1);
                MovePositionTo(SelectionPosition(start - len1 + len2));
-               delete []line1;
-               delete []line2;
        }
 }
 
@@ -5058,11 +5069,10 @@ void Editor::Duplicate(bool forLine) {
                        start = SelectionPosition(pdoc->LineStart(line));
                        end = SelectionPosition(pdoc->LineEnd(line));
                }
-               char *text = CopyRange(start.Position(), end.Position());
+               std::string text = RangeText(start.Position(), end.Position());
                if (forLine)
                        pdoc->InsertString(end.Position(), eol, eolLen);
-               pdoc->InsertString(end.Position() + eolLen, text, SelectionRange(end, start).Length());
-               delete []text;
+               pdoc->InsertString(end.Position() + eolLen, text.c_str(), SelectionRange(end, 
start).Length());
        }
        if (sel.Count() && sel.IsRectangular()) {
                SelectionPosition last = sel.Last();
@@ -5742,13 +5752,13 @@ int Editor::KeyDown(int key, bool shift, bool ctrl, bool alt, bool *consumed) {
 }
 
 void Editor::Indent(bool forwards) {
+       UndoGroup ug(pdoc);
        for (size_t r=0; r<sel.Count(); r++) {
                int lineOfAnchor = pdoc->LineFromPosition(sel.Range(r).anchor.Position());
                int caretPosition = sel.Range(r).caret.Position();
                int lineCurrentPos = pdoc->LineFromPosition(caretPosition);
                if (lineOfAnchor == lineCurrentPos) {
                        if (forwards) {
-                               UndoGroup ug(pdoc);
                                pdoc->DeleteChars(sel.Range(r).Start().Position(), sel.Range(r).Length());
                                caretPosition = sel.Range(r).caret.Position();
                                if (pdoc->GetColumn(caretPosition) <= 
pdoc->GetColumn(pdoc->GetLineIndentPosition(lineCurrentPos)) &&
@@ -5775,7 +5785,6 @@ void Editor::Indent(bool forwards) {
                        } else {
                                if (pdoc->GetColumn(caretPosition) <= 
pdoc->GetLineIndentation(lineCurrentPos) &&
                                                pdoc->tabIndents) {
-                                       UndoGroup ug(pdoc);
                                        int indentation = pdoc->GetLineIndentation(lineCurrentPos);
                                        int indentationStep = pdoc->IndentSize();
                                        pdoc->SetLineIndentation(lineCurrentPos, indentation - 
indentationStep);
@@ -5799,10 +5808,7 @@ void Editor::Indent(bool forwards) {
                        int lineBottomSel = Platform::Maximum(lineOfAnchor, lineCurrentPos);
                        if (pdoc->LineStart(lineBottomSel) == sel.Range(r).anchor.Position() || 
pdoc->LineStart(lineBottomSel) == caretPosition)
                                lineBottomSel--;        // If not selecting any characters on a line, do not 
indent
-                       {
-                               UndoGroup ug(pdoc);
-                               pdoc->Indent(forwards, lineBottomSel, lineTopSel);
-                       }
+                       pdoc->Indent(forwards, lineBottomSel, lineTopSel);
                        if (lineOfAnchor < lineCurrentPos) {
                                if (currentPosPosOnLine == 0)
                                        sel.Range(r) = SelectionRange(pdoc->LineStart(lineCurrentPos), 
pdoc->LineStart(lineOfAnchor));
@@ -5973,19 +5979,6 @@ static bool Close(Point pt1, Point pt2) {
        return true;
 }
 
-char *Editor::CopyRange(int start, int end) {
-       char *text = 0;
-       if (start < end) {
-               int len = end - start;
-               text = new char[len + 1];
-               for (int i = 0; i < len; i++) {
-                       text[i] = pdoc->CharAt(start + i);
-               }
-               text[len] = '\0';
-       }
-       return text;
-}
-
 std::string Editor::RangeText(int start, int end) const {
        if (start < end) {
                int len = end - start;
@@ -6005,55 +5998,30 @@ void Editor::CopySelectionRange(SelectionText *ss, bool allowLineCopy) {
                        int start = pdoc->LineStart(currentLine);
                        int end = pdoc->LineEnd(currentLine);
 
-                       char *text = CopyRange(start, end);
-                       size_t textLen = text ? strlen(text) : 0;
-                       // include room for \r\n\0
-                       textLen += 3;
-                       char *textWithEndl = new char[textLen];
-                       textWithEndl[0] = '\0';
-                       if (text)
-                               strcat(textWithEndl, text);
+                       std::string text = RangeText(start, end);
                        if (pdoc->eolMode != SC_EOL_LF)
-                               strcat(textWithEndl, "\r");
+                               text.push_back('\r');
                        if (pdoc->eolMode != SC_EOL_CR)
-                               strcat(textWithEndl, "\n");
-                       ss->Set(textWithEndl, static_cast<int>(strlen(textWithEndl) + 1),
-                               pdoc->dbcsCodePage, vs.styles[STYLE_DEFAULT].characterSet, false, true);
-                       delete []text;
+                               text.push_back('\n');
+                       ss->Copy(text, pdoc->dbcsCodePage,
+                               vs.styles[STYLE_DEFAULT].characterSet, false, true);
                }
        } else {
-               int delimiterLength = 0;
-               if (sel.selType == Selection::selRectangle) {
-                       if (pdoc->eolMode == SC_EOL_CRLF) {
-                               delimiterLength = 2;
-                       } else {
-                               delimiterLength = 1;
-                       }
-               }
-               size_t size = sel.Length() + delimiterLength * sel.Count();
-               char *text = new char[size + 1];
-               int j = 0;
+               std::string text;
                std::vector<SelectionRange> rangesInOrder = sel.RangesCopy();
                if (sel.selType == Selection::selRectangle)
                        std::sort(rangesInOrder.begin(), rangesInOrder.end());
                for (size_t r=0; r<rangesInOrder.size(); r++) {
                        SelectionRange current = rangesInOrder[r];
-                       for (int i = current.Start().Position();
-                               i < current.End().Position();
-                               i++) {
-                               text[j++] = pdoc->CharAt(i);
-                       }
+                       text.append(RangeText(current.Start().Position(), current.End().Position()));
                        if (sel.selType == Selection::selRectangle) {
-                               if (pdoc->eolMode != SC_EOL_LF) {
-                                       text[j++] = '\r';
-                               }
-                               if (pdoc->eolMode != SC_EOL_CR) {
-                                       text[j++] = '\n';
-                               }
+                               if (pdoc->eolMode != SC_EOL_LF)
+                                       text.push_back('\r');
+                               if (pdoc->eolMode != SC_EOL_CR)
+                                       text.push_back('\n');
                        }
                }
-               text[size] = '\0';
-               ss->Set(text, static_cast<int>(size + 1), pdoc->dbcsCodePage,
+               ss->Copy(text, pdoc->dbcsCodePage,
                        vs.styles[STYLE_DEFAULT].characterSet, sel.IsRectangular(), sel.selType == 
Selection::selLines);
        }
 }
@@ -6062,14 +6030,15 @@ void Editor::CopyRangeToClipboard(int start, int end) {
        start = pdoc->ClampPositionIntoDocument(start);
        end = pdoc->ClampPositionIntoDocument(end);
        SelectionText selectedText;
-       selectedText.Set(CopyRange(start, end), end - start + 1,
+       std::string text = RangeText(start, end);
+       selectedText.Copy(text,
                pdoc->dbcsCodePage, vs.styles[STYLE_DEFAULT].characterSet, false, false);
        CopyToClipboard(selectedText);
 }
 
 void Editor::CopyText(int length, const char *text) {
        SelectionText selectedText;
-       selectedText.Copy(text, length + 1,
+       selectedText.Copy(std::string(text, length),
                pdoc->dbcsCodePage, vs.styles[STYLE_DEFAULT].characterSet, false, false);
        CopyToClipboard(selectedText);
 }
@@ -6108,7 +6077,7 @@ void Editor::StartDrag() {
        //DisplayCursor(Window::cursorArrow);
 }
 
-void Editor::DropAt(SelectionPosition position, const char *value, bool moving, bool rectangular) {
+void Editor::DropAt(SelectionPosition position, const char *value, size_t lengthValue, bool moving, bool 
rectangular) {
        //Platform::DebugPrintf("DropAt %d %d\n", inDragDrop, position);
        if (inDragDrop == ddDragging)
                dropWentOutside = false;
@@ -6149,15 +6118,15 @@ void Editor::DropAt(SelectionPosition position, const char *value, bool moving,
                position = positionAfterDeletion;
 
                if (rectangular) {
-                       PasteRectangular(position, value, istrlen(value));
+                       PasteRectangular(position, value, static_cast<int>(lengthValue));
                        // Should try to select new rectangle but it may not be a rectangle now so just 
select the drop position
                        SetEmptySelection(position);
                } else {
                        position = MovePositionOutsideChar(position, sel.MainCaret() - position.Position());
                        position = SelectionPosition(InsertSpace(position.Position(), 
position.VirtualSpace()));
-                       if (pdoc->InsertCString(position.Position(), value)) {
+                       if (pdoc->InsertString(position.Position(), value, static_cast<int>(lengthValue))) {
                                SelectionPosition posAfterInsertion = position;
-                               posAfterInsertion.Add(istrlen(value));
+                               posAfterInsertion.Add(static_cast<int>(lengthValue));
                                SetSelection(posAfterInsertion, position);
                        }
                }
@@ -6166,6 +6135,10 @@ void Editor::DropAt(SelectionPosition position, const char *value, bool moving,
        }
 }
 
+void Editor::DropAt(SelectionPosition position, const char *value, bool moving, bool rectangular) {
+       DropAt(position, value, strlen(value), moving, rectangular);
+}
+
 /**
  * @return true if given position is inside the selection,
  */
@@ -6216,7 +6189,7 @@ bool Editor::PointInSelMargin(Point pt) {
        }
 }
 
-Window::Cursor Editor::GetMarginCursor(Point pt) {
+Window::Cursor Editor::GetMarginCursor(Point pt) const {
        int x = 0;
        for (int margin = 0; margin <= SC_MAX_MARGIN; margin++) {
                if ((pt.x >= x) && (pt.x < x + vs.ms[margin].width))
@@ -6347,7 +6320,7 @@ void Editor::ButtonDown(Point pt, unsigned int curTime, bool shift, bool ctrl, b
                        if (inSelMargin) {
                                // Inside margin selection type should be either selSubLine or selWholeLine.
                                if (selectionType == selSubLine) {
-                                       // If it is selSubLine, we're inside a *double* click and word wrap 
is enabled, 
+                                       // If it is selSubLine, we're inside a *double* click and word wrap 
is enabled,
                                        // so we switch to selWholeLine in order to select whole line.
                                        selectionType = selWholeLine;
                                } else if (selectionType != selSubLine && selectionType != selWholeLine) {
@@ -6359,7 +6332,7 @@ void Editor::ButtonDown(Point pt, unsigned int curTime, bool shift, bool ctrl, b
                                        selectionType = selWord;
                                        doubleClick = true;
                                } else if (selectionType == selWord) {
-                                       // Since we ended up here, we're inside a *triple* click, which 
should always select 
+                                       // Since we ended up here, we're inside a *triple* click, which 
should always select
                                        // whole line irregardless of word wrap being enabled or not.
                                        selectionType = selWholeLine;
                                } else {
@@ -6424,7 +6397,7 @@ void Editor::ButtonDown(Point pt, unsigned int curTime, bool shift, bool ctrl, b
                                        lineAnchorPos = sel.MainAnchor() - 1;
                                else
                                        lineAnchorPos = sel.MainAnchor();
-                               // Reset selection type if there is an empty selection. 
+                               // Reset selection type if there is an empty selection.
                                // This ensures that we don't end up stuck in previous selection mode, which 
is no longer valid.
                                // Otherwise, if there's a non empty selection, reset selection type only if 
it differs from selSubLine and selWholeLine.
                                // This ensures that we continue selecting in the same selection mode.
@@ -6482,7 +6455,7 @@ void Editor::ButtonDown(Point pt, unsigned int curTime, bool shift, bool ctrl, b
        ShowCaretAtCurrentPosition();
 }
 
-bool Editor::PositionIsHotspot(int position) {
+bool Editor::PositionIsHotspot(int position) const {
        return vs.styles[pdoc->StyleAt(position) & pdoc->stylingBitsMask].hotspot;
 }
 
@@ -6526,7 +6499,7 @@ void Editor::SetHotSpotRange(Point *pt) {
        }
 }
 
-void Editor::GetHotSpotRange(int &hsStart_, int &hsEnd_) {
+void Editor::GetHotSpotRange(int &hsStart_, int &hsEnd_) const {
        hsStart_ = hsStart;
        hsEnd_ = hsEnd;
 }
@@ -6671,26 +6644,26 @@ void Editor::ButtonUp(Point pt, unsigned int curTime, bool ctrl) {
                        SelectionPosition selStart = SelectionStart();
                        SelectionPosition selEnd = SelectionEnd();
                        if (selStart < selEnd) {
-                               if (drag.len) {
+                               if (drag.Length()) {
                                        if (ctrl) {
-                                               if (pdoc->InsertString(newPos.Position(), drag.s, drag.len)) {
-                                                       SetSelection(newPos.Position(), newPos.Position() + 
drag.len);
+                                               if (pdoc->InsertString(newPos.Position(), drag.Data(), 
static_cast<int>(drag.Length()))) {
+                                                       SetSelection(newPos.Position(), newPos.Position() + 
static_cast<int>(drag.Length()));
                                                }
                                        } else if (newPos < selStart) {
-                                               pdoc->DeleteChars(selStart.Position(), drag.len);
-                                               if (pdoc->InsertString(newPos.Position(), drag.s, drag.len)) {
-                                                       SetSelection(newPos.Position(), newPos.Position() + 
drag.len);
+                                               pdoc->DeleteChars(selStart.Position(), 
static_cast<int>(drag.Length()));
+                                               if (pdoc->InsertString(newPos.Position(), drag.Data(), 
static_cast<int>(drag.Length()))) {
+                                                       SetSelection(newPos.Position(), newPos.Position() + 
static_cast<int>(drag.Length()));
                                                }
                                        } else if (newPos > selEnd) {
-                                               pdoc->DeleteChars(selStart.Position(), drag.len);
-                                               newPos.Add(-drag.len);
-                                               if (pdoc->InsertString(newPos.Position(), drag.s, drag.len)) {
-                                                       SetSelection(newPos.Position(), newPos.Position() + 
drag.len);
+                                               pdoc->DeleteChars(selStart.Position(), 
static_cast<int>(drag.Length()));
+                                               newPos.Add(-static_cast<int>(drag.Length()));
+                                               if (pdoc->InsertString(newPos.Position(), drag.Data(), 
static_cast<int>(drag.Length()))) {
+                                                       SetSelection(newPos.Position(), newPos.Position() + 
static_cast<int>(drag.Length()));
                                                }
                                        } else {
                                                SetEmptySelection(newPos.Position());
                                        }
-                                       drag.Free();
+                                       drag.Clear();
                                }
                                selectionType = selChar;
                        }
@@ -6759,9 +6732,9 @@ bool Editor::Idle() {
 
        if (!wrappingDone) {
                // Wrap lines during idle.
-               WrapLines(false, -1);
+               WrapLines(wsIdle);
                // No more wrapping
-               if (wrapStart == wrapEnd)
+               if (!wrapPending.NeedsWrap())
                        wrappingDone = true;
        }
 
@@ -6786,7 +6759,7 @@ void Editor::SetFocusState(bool focusState) {
        }
 }
 
-int Editor::PositionAfterArea(PRectangle rcArea) {
+int Editor::PositionAfterArea(PRectangle rcArea) const {
        // The start of the document line after the display line after the area
        // This often means that the line after a modification is restyled which helps
        // detect multiline comment additions and heals single line comments
@@ -6862,6 +6835,7 @@ void Editor::CheckForChangeOutsidePaint(Range r) {
 
                if (!PaintContains(rcRange)) {
                        AbandonPaint();
+                       paintAbandonedByStyling = true;
                }
        }
 }
@@ -6960,34 +6934,42 @@ void Editor::SetAnnotationVisible(int visible) {
 /**
  * Recursively expand a fold, making lines visible except where they have an unexpanded parent.
  */
-void Editor::Expand(int &line, bool doExpand) {
+int Editor::ExpandLine(int line) {
        int lineMaxSubord = pdoc->GetLastChild(line);
        line++;
        while (line <= lineMaxSubord) {
-               if (doExpand)
-                       cs.SetVisible(line, line, true);
+               cs.SetVisible(line, line, true);
                int level = pdoc->GetLevel(line);
                if (level & SC_FOLDLEVELHEADERFLAG) {
-                       if (doExpand && cs.GetExpanded(line)) {
-                               Expand(line, true);
+                       if (cs.GetExpanded(line)) {
+                               line = ExpandLine(line);
                        } else {
-                               Expand(line, false);
+                               line = pdoc->GetLastChild(line);
                        }
-               } else {
-                       line++;
                }
+               line++;
+       }
+       return lineMaxSubord;
+}
+
+void Editor::SetFoldExpanded(int lineDoc, bool expanded) {
+       if (cs.SetExpanded(lineDoc, expanded)) {
+               RedrawSelMargin();
        }
 }
 
-void Editor::ToggleContraction(int line) {
+void Editor::FoldLine(int line, int action) {
        if (line >= 0) {
-               if ((pdoc->GetLevel(line) & SC_FOLDLEVELHEADERFLAG) == 0) {
-                       line = pdoc->GetFoldParent(line);
-                       if (line < 0)
-                               return;
+               if (action == SC_FOLDACTION_TOGGLE) {
+                       if ((pdoc->GetLevel(line) & SC_FOLDLEVELHEADERFLAG) == 0) {
+                               line = pdoc->GetFoldParent(line);
+                               if (line < 0)
+                                       return;
+                       }
+                       action = (cs.GetExpanded(line)) ? SC_FOLDACTION_CONTRACT : SC_FOLDACTION_EXPAND;
                }
 
-               if (cs.GetExpanded(line)) {
+               if (action == SC_FOLDACTION_CONTRACT) {
                        int lineMaxSubord = pdoc->GetLastChild(line);
                        if (lineMaxSubord > line) {
                                cs.SetExpanded(line, 0);
@@ -6998,9 +6980,6 @@ void Editor::ToggleContraction(int line) {
                                        // This does not re-expand the fold
                                        EnsureCaretVisible();
                                }
-
-                               SetScrollBars();
-                               Redraw();
                        }
 
                } else {
@@ -7009,14 +6988,38 @@ void Editor::ToggleContraction(int line) {
                                GoToLine(line);
                        }
                        cs.SetExpanded(line, 1);
-                       Expand(line, true);
-                       SetScrollBars();
-                       Redraw();
+                       ExpandLine(line);
                }
+
+               SetScrollBars();
+               Redraw();
        }
 }
 
-int Editor::ContractedFoldNext(int lineStart) {
+void Editor::FoldExpand(int line, int action, int level) {
+       bool expanding = action == SC_FOLDACTION_EXPAND;
+       if (action == SC_FOLDACTION_TOGGLE) {
+               expanding = !cs.GetExpanded(line);
+       }
+       SetFoldExpanded(line, expanding);
+       if (expanding && (cs.HiddenLines() == 0))
+               // Nothing to do
+               return;
+       int lineMaxSubord = pdoc->GetLastChild(line, level & SC_FOLDLEVELNUMBERMASK);
+       line++;
+       cs.SetVisible(line, lineMaxSubord, expanding);
+       while (line <= lineMaxSubord) {
+               int levelLine = pdoc->GetLevel(line);
+               if (levelLine & SC_FOLDLEVELHEADERFLAG) {
+                       SetFoldExpanded(line, expanding);
+               }
+               line++;
+       }
+       SetScrollBars();
+       Redraw();
+}
+
+int Editor::ContractedFoldNext(int lineStart) const {
        for (int line = lineStart; line<pdoc->LinesTotal();) {
                if (!cs.GetExpanded(line) && (pdoc->GetLevel(line) & SC_FOLDLEVELHEADERFLAG))
                        return line;
@@ -7035,11 +7038,11 @@ int Editor::ContractedFoldNext(int lineStart) {
 void Editor::EnsureLineVisible(int lineDoc, bool enforcePolicy) {
 
        // In case in need of wrapping to ensure DisplayFromDoc works.
-       if (lineDoc >= wrapStart)
-               WrapLines(true, -1);
+       if (lineDoc >= wrapPending.start)
+               WrapLines(wsAll);
 
        if (!cs.GetVisible(lineDoc)) {
-               // Back up to find a non-blank line 
+               // Back up to find a non-blank line
                int lookLine = lineDoc;
                int lookLineLevel = pdoc->GetLevel(lookLine);
                while ((lookLine > 0) && (lookLineLevel & SC_FOLDLEVELWHITEFLAG)) {
@@ -7047,7 +7050,7 @@ void Editor::EnsureLineVisible(int lineDoc, bool enforcePolicy) {
                }
                int lineParent = pdoc->GetFoldParent(lookLine);
                if (lineParent < 0) {
-                       // Backed up to a top level line, so try to find parent of initial line 
+                       // Backed up to a top level line, so try to find parent of initial line
                        lineParent = pdoc->GetFoldParent(lineDoc);
                }
                if (lineParent >= 0) {
@@ -7055,7 +7058,7 @@ void Editor::EnsureLineVisible(int lineDoc, bool enforcePolicy) {
                                EnsureLineVisible(lineParent, enforcePolicy);
                        if (!cs.GetExpanded(lineParent)) {
                                cs.SetExpanded(lineParent, 1);
-                               Expand(lineParent, true);
+                               ExpandLine(lineParent);
                        }
                }
                SetScrollBars();
@@ -7084,6 +7087,89 @@ void Editor::EnsureLineVisible(int lineDoc, bool enforcePolicy) {
        }
 }
 
+void Editor::FoldAll(int action) {
+       pdoc->EnsureStyledTo(pdoc->Length());
+       int maxLine = pdoc->LinesTotal();
+       bool expanding = action == SC_FOLDACTION_EXPAND;
+       if (action == SC_FOLDACTION_TOGGLE) {
+               // Discover current state
+               for (int lineSeek = 0; lineSeek < maxLine; lineSeek++) {
+                       if (pdoc->GetLevel(lineSeek) & SC_FOLDLEVELHEADERFLAG) {
+                               expanding = !cs.GetExpanded(lineSeek);
+                               break;
+                       }
+               }
+       }
+       if (expanding) {
+               cs.SetVisible(0, maxLine-1, true);
+               for (int line = 0; line < maxLine; line++) {
+                       int levelLine = pdoc->GetLevel(line);
+                       if (levelLine & SC_FOLDLEVELHEADERFLAG) {
+                               SetFoldExpanded(line, true);
+                       }
+               }
+       } else {
+               for (int line = 0; line < maxLine; line++) {
+                       int level = pdoc->GetLevel(line);
+                       if ((level & SC_FOLDLEVELHEADERFLAG) &&
+                                       (SC_FOLDLEVELBASE == (level & SC_FOLDLEVELNUMBERMASK))) {
+                               SetFoldExpanded(line, false);
+                               int lineMaxSubord = pdoc->GetLastChild(line, -1);
+                               if (lineMaxSubord > line) {
+                                       cs.SetVisible(line + 1, lineMaxSubord, false);
+                               }
+                       }
+               }
+       }
+       SetScrollBars();
+       Redraw();
+}
+
+void Editor::FoldChanged(int line, int levelNow, int levelPrev) {
+       if (levelNow & SC_FOLDLEVELHEADERFLAG) {
+               if (!(levelPrev & SC_FOLDLEVELHEADERFLAG)) {
+                       // Adding a fold point.
+                       if (cs.SetExpanded(line, true)) {
+                               RedrawSelMargin();
+                       }
+                       FoldExpand(line, SC_FOLDACTION_EXPAND, levelPrev);
+               }
+       } else if (levelPrev & SC_FOLDLEVELHEADERFLAG) {
+               if (!cs.GetExpanded(line)) {
+                       // Removing the fold from one that has been contracted so should expand
+                       // otherwise lines are left invisible with no way to make them visible
+                       if (cs.SetExpanded(line, true)) {
+                               RedrawSelMargin();
+                       }
+                       FoldExpand(line, SC_FOLDACTION_EXPAND, levelPrev);
+               }
+       }
+       if (!(levelNow & SC_FOLDLEVELWHITEFLAG) &&
+               ((levelPrev & SC_FOLDLEVELNUMBERMASK) > (levelNow & SC_FOLDLEVELNUMBERMASK))) {
+               if (cs.HiddenLines()) {
+                       // See if should still be hidden
+                       int parentLine = pdoc->GetFoldParent(line);
+                       if ((parentLine < 0) || (cs.GetExpanded(parentLine) && cs.GetVisible(parentLine))) {
+                               cs.SetVisible(line, line, true);
+                               SetScrollBars();
+                               Redraw();
+                       }
+               }
+       }
+}
+
+void Editor::NeedShown(int pos, int len) {
+       if (foldAutomatic & SC_AUTOMATICFOLD_SHOW) {
+               int lineStart = pdoc->LineFromPosition(pos);
+               int lineEnd = pdoc->LineFromPosition(pos+len);
+               for (int line = lineStart; line <= lineEnd; line++) {
+                       EnsureLineVisible(line, false);
+               }
+       } else {
+               NotifyNeedShown(pos, len);
+       }
+}
+
 int Editor::GetTag(char *tagValue, int tagNumber) {
        const char *text = 0;
        int length = 0;
@@ -7146,18 +7232,17 @@ int Editor::WrapCount(int line) {
 void Editor::AddStyledText(char *buffer, int appendLength) {
        // The buffer consists of alternating character bytes and style bytes
        int textLength = appendLength / 2;
-       char *text = new char[textLength];
+       std::string text(textLength, '\0');
        int i;
        for (i = 0; i < textLength; i++) {
                text[i] = buffer[i*2];
        }
-       pdoc->InsertString(CurrentPosition(), text, textLength);
+       pdoc->InsertString(CurrentPosition(), text.c_str(), textLength);
        for (i = 0; i < textLength; i++) {
                text[i] = buffer[i*2+1];
        }
        pdoc->StartStyling(CurrentPosition(), static_cast<char>(0xff));
-       pdoc->SetStyles(textLength, text);
-       delete []text;
+       pdoc->SetStyles(textLength, text.c_str());
        SetEmptySelection(sel.MainCaret() + textLength);
 }
 
@@ -7417,13 +7502,13 @@ sptr_t Editor::WndProc(unsigned int iMessage, uptr_t wParam, sptr_t lParam) {
                        SelectionText selectedText;
                        CopySelectionRange(&selectedText);
                        if (lParam == 0) {
-                               return selectedText.len ? selectedText.len : 1;
+                               return selectedText.LengthWithTerminator();
                        } else {
                                char *ptr = CharPtrFromSPtr(lParam);
-                               int iChar = 0;
-                               if (selectedText.len) {
-                                       for (; iChar < selectedText.len; iChar++)
-                                               ptr[iChar] = selectedText.s[iChar];
+                               unsigned int iChar = 0;
+                               if (selectedText.Length()) {
+                                       for (; iChar < selectedText.LengthWithTerminator(); iChar++)
+                                               ptr[iChar] = selectedText.Data()[iChar];
                                } else {
                                        ptr[0] = '\0';
                                }
@@ -7905,10 +7990,10 @@ sptr_t Editor::WndProc(unsigned int iMessage, uptr_t wParam, sptr_t lParam) {
 
        case SCI_GETLINEENDTYPESALLOWED:
                return pdoc->GetLineEndTypesAllowed();
-               
+
        case SCI_GETLINEENDTYPESACTIVE:
                return pdoc->GetLineEndTypesActive();
-               
+
        case SCI_STARTSTYLING:
                pdoc->StartStyling(wParam, static_cast<char>(lParam));
                break;
@@ -8121,7 +8206,7 @@ sptr_t Editor::WndProc(unsigned int iMessage, uptr_t wParam, sptr_t lParam) {
                break;
 
        case SCI_TEXTWIDTH:
-               PLATFORM_ASSERT(wParam < vs.stylesSize);
+               PLATFORM_ASSERT(wParam < vs.styles.size());
                PLATFORM_ASSERT(lParam);
                return TextWidth(wParam, CharPtrFromSPtr(lParam));
 
@@ -8290,7 +8375,7 @@ sptr_t Editor::WndProc(unsigned int iMessage, uptr_t wParam, sptr_t lParam) {
        case SCI_MARKERGET:
                return pdoc->GetMark(wParam);
 
-       case SCI_MARKERNEXT: 
+       case SCI_MARKERNEXT:
                return pdoc->MarkerNext(wParam, lParam);
 
        case SCI_MARKERPREVIOUS: {
@@ -8531,21 +8616,42 @@ sptr_t Editor::WndProc(unsigned int iMessage, uptr_t wParam, sptr_t lParam) {
                return cs.HiddenLines() ? 0 : 1;
 
        case SCI_SETFOLDEXPANDED:
-               if (cs.SetExpanded(wParam, lParam != 0)) {
-                       RedrawSelMargin();
-               }
+               SetFoldExpanded(wParam, lParam != 0);
                break;
 
        case SCI_GETFOLDEXPANDED:
                return cs.GetExpanded(wParam);
 
+       case SCI_SETAUTOMATICFOLD:
+               foldAutomatic = wParam;
+               break;
+
+       case SCI_GETAUTOMATICFOLD:
+               return foldAutomatic;
+
        case SCI_SETFOLDFLAGS:
                foldFlags = wParam;
                Redraw();
                break;
 
        case SCI_TOGGLEFOLD:
-               ToggleContraction(wParam);
+               FoldLine(wParam, SC_FOLDACTION_TOGGLE);
+               break;
+
+       case SCI_FOLDLINE:
+               FoldLine(wParam, lParam);
+               break;
+
+       case SCI_FOLDCHILDREN:
+               FoldExpand(wParam, lParam, pdoc->GetLevel(wParam));
+               break;
+
+       case SCI_FOLDALL:
+               FoldAll(wParam);
+               break;
+
+       case SCI_EXPANDCHILDREN:
+               FoldExpand(wParam, SC_FOLDACTION_EXPAND, lParam);
                break;
 
        case SCI_CONTRACTEDFOLDNEXT:
@@ -8559,7 +8665,7 @@ sptr_t Editor::WndProc(unsigned int iMessage, uptr_t wParam, sptr_t lParam) {
                EnsureLineVisible(wParam, true);
                break;
 
-       case SCI_SCROLLRANGE: 
+       case SCI_SCROLLRANGE:
                ScrollRange(SelectionRange(lParam, wParam));
                break;
 
@@ -8932,9 +9038,7 @@ sptr_t Editor::WndProc(unsigned int iMessage, uptr_t wParam, sptr_t lParam) {
 
        case SCI_CREATEDOCUMENT: {
                        Document *doc = new Document();
-                       if (doc) {
-                               doc->AddRef();
-                       }
+                       doc->AddRef();
                        return reinterpret_cast<sptr_t>(doc);
                }
 
@@ -8948,11 +9052,9 @@ sptr_t Editor::WndProc(unsigned int iMessage, uptr_t wParam, sptr_t lParam) {
 
        case SCI_CREATELOADER: {
                        Document *doc = new Document();
-                       if (doc) {
-                               doc->AddRef();
-                               doc->Allocate(wParam);
-                               doc->SetUndoCollection(false);
-                       }
+                       doc->AddRef();
+                       doc->Allocate(wParam);
+                       doc->SetUndoCollection(false);
                        return reinterpret_cast<sptr_t>(static_cast<ILoader *>(doc));
                }
 
@@ -9497,18 +9599,18 @@ sptr_t Editor::WndProc(unsigned int iMessage, uptr_t wParam, sptr_t lParam) {
        case SCI_CHANGELEXERSTATE:
                pdoc->ChangeLexerState(wParam, lParam);
                break;
-       
+
        case SCI_SETIDENTIFIER:
                SetCtrlID(wParam);
                break;
-       
+
        case SCI_GETIDENTIFIER:
                return GetCtrlID();
 
        case SCI_SETTECHNOLOGY:
                // No action by default
                break;
-       
+
        case SCI_GETTECHNOLOGY:
                return technology;
 
diff --git a/plugins/scintilla/scintilla/src/Editor.h b/plugins/scintilla/scintilla/src/Editor.h
index f2b452a..3a1456a 100644
--- a/plugins/scintilla/scintilla/src/Editor.h
+++ b/plugins/scintilla/scintilla/src/Editor.h
@@ -75,45 +75,27 @@ public:
 };
 
 /**
- * Hold a piece of text selected for copying or dragging.
- * The text is expected to hold a terminating '\0' and this is counted in len.
+ * Hold a piece of text selected for copying or dragging, along with encoding and selection format 
information.
  */
 class SelectionText {
+       std::string s;
 public:
-       char *s;
-       int len;
        bool rectangular;
        bool lineCopy;
        int codePage;
        int characterSet;
-       SelectionText() : s(0), len(0), rectangular(false), lineCopy(false), codePage(0), characterSet(0) {}
+       SelectionText() : rectangular(false), lineCopy(false), codePage(0), characterSet(0) {}
        ~SelectionText() {
-               Free();
        }
-       void Free() {
-               Set(0, 0, 0, 0, false, false);
+       void Clear() {
+               s.clear();
+               rectangular = false;
+               lineCopy = false;
+               codePage = 0;
+               characterSet = 0;
        }
-       void Set(char *s_, int len_, int codePage_, int characterSet_, bool rectangular_, bool lineCopy_) {
-               delete []s;
+       void Copy(const std::string &s_, int codePage_, int characterSet_, bool rectangular_, bool lineCopy_) 
{
                s = s_;
-               if (s)
-                       len = len_;
-               else
-                       len = 0;
-               codePage = codePage_;
-               characterSet = characterSet_;
-               rectangular = rectangular_;
-               lineCopy = lineCopy_;
-               FixSelectionForClipboard();
-       }
-       void Copy(const char *s_, int len_, int codePage_, int characterSet_, bool rectangular_, bool 
lineCopy_) {
-               delete []s;
-               s = 0;
-               s = new char[len_];
-               len = len_;
-               for (int i = 0; i < len_; i++) {
-                       s[i] = s_[i];
-               }
                codePage = codePage_;
                characterSet = characterSet_;
                rectangular = rectangular_;
@@ -121,18 +103,60 @@ public:
                FixSelectionForClipboard();
        }
        void Copy(const SelectionText &other) {
-               Copy(other.s, other.len, other.codePage, other.characterSet, other.rectangular, 
other.lineCopy);
+               Copy(other.s, other.codePage, other.characterSet, other.rectangular, other.lineCopy);
+       }
+       const char *Data() const {
+               return s.c_str();
+       }
+       size_t Length() const {
+               return s.length();
+       }
+       size_t LengthWithTerminator() const {
+               return s.length() + 1;
+       }
+       bool Empty() const {
+               return s.empty();
        }
-       
 private:
        void FixSelectionForClipboard() {
-               // Replace null characters by spaces.
-               // To avoid that the content of the clipboard is truncated in the paste operation 
-               // when the clipboard contains null characters.
-               for (int i = 0; i < len - 1; ++i) {
-                       if (s[i] == '\0')
-                               s[i] = ' ';
+               // To avoid truncating the contents of the clipboard when pasted where the 
+               // clipboard contains NUL characters, replace NUL characters by spaces.
+               std::replace(s.begin(), s.end(), '\0', ' ');
+       }
+};
+
+struct WrapPending {
+       // The range of lines that need to be wrapped
+       enum { lineLarge = 0x7ffffff };
+       int start;      // When there are wraps pending, will be in document range
+       int end;        // May be lineLarge to indicate all of document after start
+       WrapPending() {
+               start = lineLarge;
+               end = lineLarge;
+       }
+       void Reset() {
+               start = lineLarge;
+               end = lineLarge;
+       }
+       void Wrapped(int line) {
+               if (start == line)
+                       start++;
+       }
+       bool NeedsWrap() const {
+               return start < end;
+       }
+       bool AddRange(int lineStart, int lineEnd) {
+               const bool neededWrap = NeedsWrap();
+               bool changed = false;
+               if (start > lineStart) {
+                       start = lineStart;
+                       changed = true;
                }
+               if ((end < lineEnd) || !neededWrap) {
+                       end = lineEnd;
+                       changed = true;
+               }
+               return changed;
        }
 };
 
@@ -170,6 +194,7 @@ protected:  // ScintillaBase subclass needs access to much of Editor
        bool hasFocus;
        bool hideSelection;
        bool inOverstrike;
+       bool drawOverstrikeCaret;
        bool mouseDownCaptures;
 
        /** In bufferedDraw mode, graphics operations are drawn to a pixmap and then copied to
@@ -249,6 +274,7 @@ protected:  // ScintillaBase subclass needs access to much of Editor
        int theEdge;
 
        enum { notPainting, painting, paintAbandoned } paintState;
+       bool paintAbandonedByStyling;
        PRectangle rcPaint;
        bool paintingAllText;
        bool willRedrawAll;
@@ -274,6 +300,7 @@ protected:  // ScintillaBase subclass needs access to much of Editor
        bool recordingMacro;
 
        int foldFlags;
+       int foldAutomatic;
        ContractionState cs;
 
        // Hotspot support
@@ -282,10 +309,8 @@ protected: // ScintillaBase subclass needs access to much of Editor
 
        // Wrapping support
        enum { eWrapNone, eWrapWord, eWrapChar } wrapState;
-       enum { wrapLineLarge = 0x7ffffff };
        int wrapWidth;
-       int wrapStart;
-       int wrapEnd;
+       WrapPending wrapPending;
        int wrapVisualFlags;
        int wrapVisualFlagsLocation;
        int wrapVisualStartIndent;
@@ -314,7 +339,7 @@ protected:  // ScintillaBase subclass needs access to much of Editor
        // scroll views where it will be equivalent to the current scroll position.
        virtual Point GetVisibleOriginInMain();
        Point DocumentPointFromView(Point ptView);  // Convert a point from view space to document
-       int TopLineOfMain();   // Return the line at Main's y coordinate 0
+       int TopLineOfMain() const;   // Return the line at Main's y coordinate 0
        virtual PRectangle GetClientRectangle();
        PRectangle GetTextRectangle();
 
@@ -330,7 +355,7 @@ protected:  // ScintillaBase subclass needs access to much of Editor
        int PositionFromLocation(Point pt, bool canReturnInvalid=false, bool charPosition=false);
        SelectionPosition SPositionFromLineX(int lineDoc, int x);
        int PositionFromLineX(int line, int x);
-       int LineFromLocation(Point pt);
+       int LineFromLocation(Point pt) const;
        void SetTopLine(int topLineNew);
 
        bool AbandonPaint();
@@ -343,8 +368,8 @@ protected:  // ScintillaBase subclass needs access to much of Editor
        bool UserVirtualSpace() const {
                return ((virtualSpaceOptions & SCVS_USERACCESSIBLE) != 0);
        }
-       int CurrentPosition();
-       bool SelectionEmpty();
+       int CurrentPosition() const;
+       bool SelectionEmpty() const;
        SelectionPosition SelectionStart();
        SelectionPosition SelectionEnd();
        void SetRectangularRange();
@@ -399,19 +424,20 @@ protected:        // ScintillaBase subclass needs access to much of Editor
        void InvalidateCaret();
        virtual void UpdateSystemCaret();
 
-       void NeedWrapping(int docLineStart = 0, int docLineEnd = wrapLineLarge);
+       void NeedWrapping(int docLineStart=0, int docLineEnd=WrapPending::lineLarge);
        bool WrapOneLine(Surface *surface, int lineToWrap);
-       bool WrapLines(bool fullWrap, int priorityWrapLineStart);
+       enum wrapScope {wsAll, wsVisible, wsIdle};
+       bool WrapLines(enum wrapScope ws);
        void LinesJoin();
        void LinesSplit(int pixelWidth);
 
-       int SubstituteMarkerIfEmpty(int markerCheck, int markerDefault);
+       int SubstituteMarkerIfEmpty(int markerCheck, int markerDefault) const;
        void PaintSelMargin(Surface *surface, PRectangle &rc);
        LineLayout *RetrieveLineLayout(int lineNumber);
        void LayoutLine(int line, Surface *surface, ViewStyle &vstyle, LineLayout *ll,
                int width=LineLayout::wrapWidthInfinite);
-       ColourDesired SelectionBackground(ViewStyle &vsDraw, bool main);
-       ColourDesired TextBackground(ViewStyle &vsDraw, bool overrideBackground, ColourDesired background, 
int inSelection, bool inHotspot, int styleMain, int i, LineLayout *ll);
+       ColourDesired SelectionBackground(ViewStyle &vsDraw, bool main) const;
+       ColourDesired TextBackground(ViewStyle &vsDraw, bool overrideBackground, ColourDesired background, 
int inSelection, bool inHotspot, int styleMain, int i, LineLayout *ll) const;
        void DrawIndentGuide(Surface *surface, int lineVisible, int lineHeight, int start, PRectangle 
rcSegment, bool highlight);
        void DrawWrapMarker(Surface *surface, PRectangle rcPlace, bool isEndMarker, ColourDesired wrapColour);
        void DrawEOL(Surface *surface, ViewStyle &vsDraw, PRectangle rcLine, LineLayout *ll,
@@ -522,7 +548,6 @@ protected:  // ScintillaBase subclass needs access to much of Editor
        void GoToLine(int lineNo);
 
        virtual void CopyToClipboard(const SelectionText &selectedText) = 0;
-       char *CopyRange(int start, int end);
        std::string RangeText(int start, int end) const;
        void CopySelectionRange(SelectionText *ss, bool allowLineCopy=false);
        void CopyRangeToClipboard(int start, int end);
@@ -531,12 +556,13 @@ protected:        // ScintillaBase subclass needs access to much of Editor
        virtual void DisplayCursor(Window::Cursor c);
        virtual bool DragThreshold(Point ptStart, Point ptNow);
        virtual void StartDrag();
+       void DropAt(SelectionPosition position, const char *value, size_t lengthValue, bool moving, bool 
rectangular);
        void DropAt(SelectionPosition position, const char *value, bool moving, bool rectangular);
        /** PositionInSelection returns true if position in selection. */
        bool PositionInSelection(int pos);
        bool PointInSelection(Point pt);
        bool PointInSelMargin(Point pt);
-       Window::Cursor GetMarginCursor(Point pt);
+       Window::Cursor GetMarginCursor(Point pt) const;
        void TrimAndSetSelection(int currentPos_, int anchor_);
        void LineSelection(int lineCurrentPos_, int lineAnchorPos_, bool wholeLine);
        void WordSelection(int pos);
@@ -554,7 +580,7 @@ protected:  // ScintillaBase subclass needs access to much of Editor
        virtual bool HaveMouseCapture() = 0;
        void SetFocusState(bool focusState);
 
-       int PositionAfterArea(PRectangle rcArea);
+       int PositionAfterArea(PRectangle rcArea) const;
        void StyleToPositionInView(Position pos);
        virtual void IdleWork();
        virtual void QueueIdleWork(WorkNeeded::workItems items, int upTo=0);
@@ -565,21 +591,27 @@ protected:        // ScintillaBase subclass needs access to much of Editor
        void SetBraceHighlight(Position pos0, Position pos1, int matchStyle);
 
        void SetAnnotationHeights(int start, int end);
-       void SetDocPointer(Document *document);
+       virtual void SetDocPointer(Document *document);
 
        void SetAnnotationVisible(int visible);
 
-       void Expand(int &line, bool doExpand);
-       void ToggleContraction(int line);
-       int ContractedFoldNext(int lineStart);
+       int ExpandLine(int line);
+       void SetFoldExpanded(int lineDoc, bool expanded);
+       void FoldLine(int line, int action);
+       void FoldExpand(int line, int action, int level);
+       int ContractedFoldNext(int lineStart) const;
        void EnsureLineVisible(int lineDoc, bool enforcePolicy);
+       void FoldChanged(int line, int levelNow, int levelPrev);
+       void NeedShown(int pos, int len);
+       void FoldAll(int action);
+
        int GetTag(char *tagValue, int tagNumber);
        int ReplaceTarget(bool replacePatterns, const char *text, int length=-1);
 
-       bool PositionIsHotspot(int position);
+       bool PositionIsHotspot(int position) const;
        bool PointIsHotspot(Point pt);
        void SetHotSpotRange(Point *pt);
-       void GetHotSpotRange(int &hsStart, int &hsEnd);
+       void GetHotSpotRange(int &hsStart, int &hsEnd) const;
 
        int CodePage() const;
        virtual bool ValidCodePage(int /* codePage */) const { return true; }
diff --git a/plugins/scintilla/scintilla/src/Indicator.cxx b/plugins/scintilla/scintilla/src/Indicator.cxx
index da75cbb..ac74351 100644
--- a/plugins/scintilla/scintilla/src/Indicator.cxx
+++ b/plugins/scintilla/scintilla/src/Indicator.cxx
@@ -152,6 +152,9 @@ void Indicator::Draw(Surface *surface, const PRectangle &rc, const PRectangle &r
                        surface->FillRectangle(rcDot, fore);
                        x += 2;
                }
+       } else if (style == INDIC_COMPOSITIONTHICK) {
+               PRectangle rcComposition(rc.left+1, rcLine.bottom-2, rc.right-1, rcLine.bottom);
+               surface->FillRectangle(rcComposition, fore);
        } else {        // Either INDIC_PLAIN or unknown
                surface->MoveTo(rc.left, ymid);
                surface->LineTo(rc.right, ymid);
diff --git a/plugins/scintilla/scintilla/src/KeyMap.cxx b/plugins/scintilla/scintilla/src/KeyMap.cxx
index 4d866d1..7407761 100644
--- a/plugins/scintilla/scintilla/src/KeyMap.cxx
+++ b/plugins/scintilla/scintilla/src/KeyMap.cxx
@@ -5,6 +5,10 @@
 // Copyright 1998-2003 by Neil Hodgson <neilh scintilla org>
 // The License.txt file describes the conditions under which this software may be distributed.
 
+#include <stdlib.h>
+
+#include <vector>
+
 #include "Platform.h"
 
 #include "Scintilla.h"
@@ -15,7 +19,7 @@
 using namespace Scintilla;
 #endif
 
-KeyMap::KeyMap() : kmap(0), len(0), alloc(0) {
+KeyMap::KeyMap() {
        for (int i = 0; MapDefault[i].key; i++) {
                AssignCmdKey(MapDefault[i].key,
                        MapDefault[i].modifiers,
@@ -28,37 +32,25 @@ KeyMap::~KeyMap() {
 }
 
 void KeyMap::Clear() {
-       delete []kmap;
-       kmap = 0;
-       len = 0;
-       alloc = 0;
+       kmap.clear();
 }
 
 void KeyMap::AssignCmdKey(int key, int modifiers, unsigned int msg) {
-       if ((len+1) >= alloc) {
-               KeyToCommand *ktcNew = new KeyToCommand[alloc + 5];
-               if (!ktcNew)
-                       return;
-               for (int k = 0; k < len; k++)
-                       ktcNew[k] = kmap[k];
-               alloc += 5;
-               delete []kmap;
-               kmap = ktcNew;
-       }
-       for (int keyIndex = 0; keyIndex < len; keyIndex++) {
+       for (size_t keyIndex = 0; keyIndex < kmap.size(); keyIndex++) {
                if ((key == kmap[keyIndex].key) && (modifiers == kmap[keyIndex].modifiers)) {
                        kmap[keyIndex].msg = msg;
                        return;
                }
        }
-       kmap[len].key = key;
-       kmap[len].modifiers = modifiers;
-       kmap[len].msg = msg;
-       len++;
+       KeyToCommand ktc;
+       ktc.key = key;
+       ktc.modifiers = modifiers;
+       ktc.msg = msg;
+       kmap.push_back(ktc);
 }
 
-unsigned int KeyMap::Find(int key, int modifiers) {
-       for (int i = 0; i < len; i++) {
+unsigned int KeyMap::Find(int key, int modifiers) const {
+       for (size_t i = 0; i < kmap.size(); i++) {
                if ((key == kmap[i].key) && (modifiers == kmap[i].modifiers)) {
                        return kmap[i].msg;
                }
diff --git a/plugins/scintilla/scintilla/src/KeyMap.h b/plugins/scintilla/scintilla/src/KeyMap.h
index f1235d8..3fbbeab 100644
--- a/plugins/scintilla/scintilla/src/KeyMap.h
+++ b/plugins/scintilla/scintilla/src/KeyMap.h
@@ -32,9 +32,7 @@ public:
 /**
  */
 class KeyMap {
-       KeyToCommand *kmap;
-       int len;
-       int alloc;
+       std::vector<KeyToCommand> kmap;
        static const KeyToCommand MapDefault[];
 
 public:
@@ -42,7 +40,7 @@ public:
        ~KeyMap();
        void Clear();
        void AssignCmdKey(int key, int modifiers, unsigned int msg);
-       unsigned int Find(int key, int modifiers);      // 0 returned on failure
+       unsigned int Find(int key, int modifiers) const;        // 0 returned on failure
 };
 
 #ifdef SCI_NAMESPACE
diff --git a/plugins/scintilla/scintilla/src/PerLine.cxx b/plugins/scintilla/scintilla/src/PerLine.cxx
index a903d6f..a066bd6 100644
--- a/plugins/scintilla/scintilla/src/PerLine.cxx
+++ b/plugins/scintilla/scintilla/src/PerLine.cxx
@@ -7,6 +7,8 @@
 
 #include <string.h>
 
+#include <algorithm>
+
 #include "Platform.h"
 
 #include "Scintilla.h"
@@ -43,17 +45,6 @@ int MarkerHandleSet::Length() const {
        return c;
 }
 
-int MarkerHandleSet::NumberFromHandle(int handle) const {
-       MarkerHandleNumber *mhn = root;
-       while (mhn) {
-               if (mhn->handle == handle) {
-                       return mhn->number;
-               }
-               mhn = mhn->next;
-       }
-       return - 1;
-}
-
 int MarkerHandleSet::MarkValue() const {
        unsigned int m = 0;
        MarkerHandleNumber *mhn = root;
@@ -77,8 +68,6 @@ bool MarkerHandleSet::Contains(int handle) const {
 
 bool MarkerHandleSet::InsertHandle(int handle, int markerNum) {
        MarkerHandleNumber *mhn = new MarkerHandleNumber;
-       if (!mhn)
-               return false;
        mhn->handle = handle;
        mhn->number = markerNum;
        mhn->next = root;
@@ -209,8 +198,6 @@ int LineMarkers::AddMark(int line, int markerNum, int lines) {
        if (!markers[line]) {
                // Need new structure to hold marker handle
                markers[line] = new MarkerHandleSet();
-               if (!markers[line])
-                       return -1;
        }
        markers[line]->InsertHandle(handleCurrent, markerNum);
 
@@ -295,7 +282,7 @@ int LineLevels::SetLevel(int line, int level, int lines) {
        return prev;
 }
 
-int LineLevels::GetLevel(int line) {
+int LineLevels::GetLevel(int line) const {
        if (levels.Length() && (line >= 0) && (line < levels.Length())) {
                return levels[line];
        } else {
@@ -338,7 +325,7 @@ int LineState::GetLineState(int line) {
        return lineStates[line];
 }
 
-int LineState::GetMaxLineState() {
+int LineState::GetMaxLineState() const {
        return lineStates.Length();
 }
 
@@ -389,10 +376,6 @@ void LineAnnotation::RemoveLine(int line) {
        }
 }
 
-bool LineAnnotation::AnySet() const {
-       return annotations.Length() > 0;
-}
-
 bool LineAnnotation::MultipleStyles(int line) const {
        if (annotations.Length() && (line >= 0) && (line < annotations.Length()) && annotations[line])
                return reinterpret_cast<AnnotationHeader *>(annotations[line])->style == IndividualStyles;
@@ -400,7 +383,7 @@ bool LineAnnotation::MultipleStyles(int line) const {
                return 0;
 }
 
-int LineAnnotation::Style(int line) {
+int LineAnnotation::Style(int line) const {
        if (annotations.Length() && (line >= 0) && (line < annotations.Length()) && annotations[line])
                return reinterpret_cast<AnnotationHeader *>(annotations[line])->style;
        else
diff --git a/plugins/scintilla/scintilla/src/PerLine.h b/plugins/scintilla/scintilla/src/PerLine.h
index 50ce1e5..70d0023 100644
--- a/plugins/scintilla/scintilla/src/PerLine.h
+++ b/plugins/scintilla/scintilla/src/PerLine.h
@@ -32,7 +32,6 @@ public:
        MarkerHandleSet();
        ~MarkerHandleSet();
        int Length() const;
-       int NumberFromHandle(int handle) const;
        int MarkValue() const;  ///< Bit set of marker numbers.
        bool Contains(int handle) const;
        bool InsertHandle(int handle, int markerNum);
@@ -73,7 +72,7 @@ public:
        void ExpandLevels(int sizeNew=-1);
        void ClearLevels();
        int SetLevel(int line, int level, int lines);
-       int GetLevel(int line);
+       int GetLevel(int line) const;
 };
 
 class LineState : public PerLine {
@@ -88,7 +87,7 @@ public:
 
        int SetLineState(int line, int state);
        int GetLineState(int line);
-       int GetMaxLineState();
+       int GetMaxLineState() const;
 };
 
 class LineAnnotation : public PerLine {
@@ -101,9 +100,8 @@ public:
        virtual void InsertLine(int line);
        virtual void RemoveLine(int line);
 
-       bool AnySet() const;
        bool MultipleStyles(int line) const;
-       int Style(int line);
+       int Style(int line) const;
        const char *Text(int line) const;
        const unsigned char *Styles(int line) const;
        void SetText(int line, const char *text);
diff --git a/plugins/scintilla/scintilla/src/PositionCache.cxx 
b/plugins/scintilla/scintilla/src/PositionCache.cxx
index 759558e..742a226 100644
--- a/plugins/scintilla/scintilla/src/PositionCache.cxx
+++ b/plugins/scintilla/scintilla/src/PositionCache.cxx
@@ -32,6 +32,7 @@
 #include "CharClassify.h"
 #include "Decoration.h"
 #include "ILexer.h"
+#include "CaseFolder.h"
 #include "Document.h"
 #include "Selection.h"
 #include "PositionCache.h"
@@ -207,7 +208,7 @@ int LineLayout::EndLineStyle() const {
 }
 
 LineLayoutCache::LineLayoutCache() :
-       level(0), length(0), size(0), cache(0),
+       level(0),
        allInvalidated(false), styleClock(-1), useCount(0) {
        Allocate(0);
 }
@@ -216,24 +217,15 @@ LineLayoutCache::~LineLayoutCache() {
        Deallocate();
 }
 
-void LineLayoutCache::Allocate(int length_) {
-       PLATFORM_ASSERT(cache == NULL);
+void LineLayoutCache::Allocate(size_t length_) {
+       PLATFORM_ASSERT(cache.empty());
        allInvalidated = false;
-       length = length_;
-       size = length;
-       if (size > 1) {
-               size = (size / 16 + 1) * 16;
-       }
-       if (size > 0) {
-               cache = new LineLayout * [size];
-       }
-       for (int i = 0; i < size; i++)
-               cache[i] = 0;
+       cache.resize(length_);
 }
 
 void LineLayoutCache::AllocateForLevel(int linesOnScreen, int linesInDoc) {
        PLATFORM_ASSERT(useCount == 0);
-       int lengthForLevel = 0;
+       size_t lengthForLevel = 0;
        if (level == llcCaret) {
                lengthForLevel = 1;
        } else if (level == llcPage) {
@@ -241,35 +233,31 @@ void LineLayoutCache::AllocateForLevel(int linesOnScreen, int linesInDoc) {
        } else if (level == llcDocument) {
                lengthForLevel = linesInDoc;
        }
-       if (lengthForLevel > size) {
+       if (lengthForLevel > cache.size()) {
                Deallocate();
                Allocate(lengthForLevel);
        } else {
-               if (lengthForLevel < length) {
-                       for (int i = lengthForLevel; i < length; i++) {
+               if (lengthForLevel < cache.size()) {
+                       for (size_t i = lengthForLevel; i < cache.size(); i++) {
                                delete cache[i];
                                cache[i] = 0;
                        }
                }
-               length = lengthForLevel;
+               cache.resize(lengthForLevel);
        }
-       PLATFORM_ASSERT(length == lengthForLevel);
-       PLATFORM_ASSERT(cache != NULL || length == 0);
+       PLATFORM_ASSERT(cache.size() == lengthForLevel);
 }
 
 void LineLayoutCache::Deallocate() {
        PLATFORM_ASSERT(useCount == 0);
-       for (int i = 0; i < length; i++)
+       for (size_t i = 0; i < cache.size(); i++)
                delete cache[i];
-       delete []cache;
-       cache = 0;
-       length = 0;
-       size = 0;
+       cache.clear();
 }
 
 void LineLayoutCache::Invalidate(LineLayout::validLevel validity_) {
-       if (cache && !allInvalidated) {
-               for (int i = 0; i < length; i++) {
+       if (!cache.empty() && !allInvalidated) {
+               for (size_t i = 0; i < cache.size(); i++) {
                        if (cache[i]) {
                                cache[i]->Invalidate(validity_);
                        }
@@ -303,15 +291,15 @@ LineLayout *LineLayoutCache::Retrieve(int lineNumber, int lineCaret, int maxChar
        } else if (level == llcPage) {
                if (lineNumber == lineCaret) {
                        pos = 0;
-               } else if (length > 1) {
-                       pos = 1 + (lineNumber % (length - 1));
+               } else if (cache.size() > 1) {
+                       pos = 1 + (lineNumber % (cache.size() - 1));
                }
        } else if (level == llcDocument) {
                pos = lineNumber;
        }
        if (pos >= 0) {
                PLATFORM_ASSERT(useCount == 0);
-               if (cache && (pos < length)) {
+               if (!cache.empty() && (pos < static_cast<int>(cache.size()))) {
                        if (cache[pos]) {
                                if ((cache[pos]->lineNumber != lineNumber) ||
                                        (cache[pos]->maxLineLength < maxChars)) {
@@ -322,12 +310,10 @@ LineLayout *LineLayoutCache::Retrieve(int lineNumber, int lineCaret, int maxChar
                        if (!cache[pos]) {
                                cache[pos] = new LineLayout(maxChars);
                        }
-                       if (cache[pos]) {
-                               cache[pos]->lineNumber = lineNumber;
-                               cache[pos]->inCache = true;
-                               ret = cache[pos];
-                               useCount++;
-                       }
+                       cache[pos]->lineNumber = lineNumber;
+                       cache[pos]->inCache = true;
+                       ret = cache[pos];
+                       useCount++;
                }
        }
 
@@ -351,33 +337,18 @@ void LineLayoutCache::Dispose(LineLayout *ll) {
 }
 
 void BreakFinder::Insert(int val) {
-       // Expand if needed
-       if (saeLen >= saeSize) {
-               saeSize *= 2;
-               int *selAndEdgeNew = new int[saeSize];
-               for (unsigned int j = 0; j<saeLen; j++) {
-                       selAndEdgeNew[j] = selAndEdge[j];
-               }
-               delete []selAndEdge;
-               selAndEdge = selAndEdgeNew;
-       }
-
        if (val >= nextBreak) {
-               for (unsigned int j = 0; j<saeLen; j++) {
-                       if (val == selAndEdge[j]) {
+               for (std::vector<int>::iterator it = selAndEdge.begin(); it != selAndEdge.end(); ++it) {
+                       if (val == *it) {
                                return;
                        }
-                       if (val < selAndEdge[j]) {
-                               for (unsigned int k = saeLen; k>j; k--) {
-                                       selAndEdge[k] = selAndEdge[k-1];
-                               }
-                               saeLen++;
-                               selAndEdge[j] = val;
+                       if (val <*it) {
+                               selAndEdge.insert(it, 1, val);
                                return;
                        }
                }
                // Not less than any so append
-               selAndEdge[saeLen++] = val;
+               selAndEdge.push_back(val);
        }
 }
 
@@ -399,17 +370,10 @@ BreakFinder::BreakFinder(LineLayout *ll_, int lineStart_, int lineEnd_, int posL
        lineEnd(lineEnd_),
        posLineStart(posLineStart_),
        nextBreak(lineStart_),
-       saeSize(0),
-       saeLen(0),
        saeCurrentPos(0),
        saeNext(0),
        subBreak(-1),
        pdoc(pdoc_) {
-       saeSize = 8;
-       selAndEdge = new int[saeSize];
-       for (unsigned int j=0; j < saeSize; j++) {
-               selAndEdge[j] = 0;
-       }
 
        // Search for first visible break
        // First find the first visible character
@@ -447,11 +411,10 @@ BreakFinder::BreakFinder(LineLayout *ll_, int lineStart_, int lineEnd_, int posL
                        Insert(pos);
                }
        }
-       saeNext = (saeLen > 0) ? selAndEdge[0] : -1;
+       saeNext = (!selAndEdge.empty()) ? selAndEdge[0] : -1;
 }
 
 BreakFinder::~BreakFinder() {
-       delete []selAndEdge;
 }
 
 int BreakFinder::First() const {
@@ -467,7 +430,7 @@ int BreakFinder::Next() {
                                        IsControlCharacter(ll->chars[nextBreak]) || 
IsControlCharacter(ll->chars[nextBreak + 1])) {
                                if (nextBreak == saeNext) {
                                        saeCurrentPos++;
-                                       saeNext = (saeLen > saeCurrentPos) ? selAndEdge[saeCurrentPos] : -1;
+                                       saeNext = (saeCurrentPos < selAndEdge.size()) ? 
selAndEdge[saeCurrentPos] : -1;
                                }
                                nextBreak++;
                                if ((nextBreak - prev) < lengthStartSubdivision) {
@@ -509,7 +472,7 @@ void PositionCacheEntry::Set(unsigned int styleNumber_, const char *s_,
        len = len_;
        clock = clock_;
        if (s_ && positions_) {
-               positions = new XYPOSITION[len + (len + 1) / 2];
+               positions = new XYPOSITION[len + (len / 4) + 1];
                for (unsigned int i=0; i<len; i++) {
                        positions[i] = static_cast<XYPOSITION>(positions_[i]);
                }
@@ -566,20 +529,18 @@ void PositionCacheEntry::ResetClock() {
 }
 
 PositionCache::PositionCache() {
-       size = 0x400;
        clock = 1;
-       pces = new PositionCacheEntry[size];
+       pces.resize(0x400);
        allClear = true;
 }
 
 PositionCache::~PositionCache() {
        Clear();
-       delete []pces;
 }
 
 void PositionCache::Clear() {
        if (!allClear) {
-               for (size_t i=0; i<size; i++) {
+               for (size_t i=0; i<pces.size(); i++) {
                        pces[i].Clear();
                }
        }
@@ -589,9 +550,7 @@ void PositionCache::Clear() {
 
 void PositionCache::SetSize(size_t size_) {
        Clear();
-       delete []pces;
-       size = size_;
-       pces = new PositionCacheEntry[size];
+       pces.resize(size_);
 }
 
 void PositionCache::MeasureWidths(Surface *surface, ViewStyle &vstyle, unsigned int styleNumber,
@@ -599,17 +558,17 @@ void PositionCache::MeasureWidths(Surface *surface, ViewStyle &vstyle, unsigned
 
        allClear = false;
        int probe = -1;
-       if ((size > 0) && (len < 30)) {
+       if ((!pces.empty()) && (len < 30)) {
                // Only store short strings in the cache so it doesn't churn with
                // long comments with only a single comment.
 
                // Two way associative: try two probe positions.
                int hashValue = PositionCacheEntry::Hash(styleNumber, s, len);
-               probe = static_cast<int>(hashValue % size);
+               probe = static_cast<int>(hashValue % pces.size());
                if (pces[probe].Retrieve(styleNumber, s, len, positions)) {
                        return;
                }
-               int probe2 = static_cast<int>((hashValue * 37) % size);
+               int probe2 = static_cast<int>((hashValue * 37) % pces.size());
                if (pces[probe2].Retrieve(styleNumber, s, len, positions)) {
                        return;
                }
@@ -639,7 +598,7 @@ void PositionCache::MeasureWidths(Surface *surface, ViewStyle &vstyle, unsigned
                if (clock > 60000) {
                        // Since there are only 16 bits for the clock, wrap it round and
                        // reset all cache entries so none get stuck with a high clock.
-                       for (size_t i=0; i<size; i++) {
+                       for (size_t i=0; i<pces.size(); i++) {
                                pces[i].ResetClock();
                        }
                        clock = 2;
diff --git a/plugins/scintilla/scintilla/src/PositionCache.h b/plugins/scintilla/scintilla/src/PositionCache.h
index ad3fffd..34f2377 100644
--- a/plugins/scintilla/scintilla/src/PositionCache.h
+++ b/plugins/scintilla/scintilla/src/PositionCache.h
@@ -73,13 +73,11 @@ public:
  */
 class LineLayoutCache {
        int level;
-       int length;
-       int size;
-       LineLayout **cache;
+       std::vector<LineLayout *>cache;
        bool allInvalidated;
        int styleClock;
        int useCount;
-       void Allocate(int length_);
+       void Allocate(size_t length_);
        void AllocateForLevel(int linesOnScreen, int linesInDoc);
 public:
        LineLayoutCache();
@@ -122,9 +120,7 @@ class BreakFinder {
        int lineEnd;
        int posLineStart;
        int nextBreak;
-       int *selAndEdge;
-       unsigned int saeSize;
-       unsigned int saeLen;
+       std::vector<int> selAndEdge;
        unsigned int saeCurrentPos;
        int saeNext;
        int subBreak;
@@ -146,8 +142,7 @@ public:
 };
 
 class PositionCache {
-       PositionCacheEntry *pces;
-       size_t size;
+       std::vector<PositionCacheEntry> pces;
        unsigned int clock;
        bool allClear;
        // Private so PositionCache objects can not be copied
@@ -157,7 +152,7 @@ public:
        ~PositionCache();
        void Clear();
        void SetSize(size_t size_);
-       size_t GetSize() const { return size; }
+       size_t GetSize() const { return pces.size(); }
        void MeasureWidths(Surface *surface, ViewStyle &vstyle, unsigned int styleNumber,
                const char *s, unsigned int len, XYPOSITION *positions, Document *pdoc);
 };
diff --git a/plugins/scintilla/scintilla/src/RESearch.cxx b/plugins/scintilla/scintilla/src/RESearch.cxx
index 87f2a69..efa23eb 100644
--- a/plugins/scintilla/scintilla/src/RESearch.cxx
+++ b/plugins/scintilla/scintilla/src/RESearch.cxx
@@ -43,10 +43,6 @@
  *
  *          int RESearch::Execute(characterIndexer &ci, int lp, int endp)
  *
- *  RESearch::Substitute:   substitute the matched portions in a new string.
- *
- *          int RESearch::Substitute(CharacterIndexer &ci, char *src, char *dst)
- *
  *  re_fail:                failure routine for RESearch::Execute. (no longer used)
  *
  *          void re_fail(char *msg, char op)
@@ -206,6 +202,8 @@
 
 #include <stdlib.h>
 
+#include <string>
+
 #include "CharClassify.h"
 #include "RESearch.h"
 
@@ -269,36 +267,29 @@ void RESearch::Init() {
        sta = NOP;                  /* status of lastpat */
        bol = 0;
        for (int i = 0; i < MAXTAG; i++)
-               pat[i] = 0;
+               pat[i].clear();
        for (int j = 0; j < BITBLK; j++)
                bittab[j] = 0;
 }
 
 void RESearch::Clear() {
        for (int i = 0; i < MAXTAG; i++) {
-               delete []pat[i];
-               pat[i] = 0;
+               pat[i].clear();
                bopat[i] = NOTFOUND;
                eopat[i] = NOTFOUND;
        }
 }
 
-bool RESearch::GrabMatches(CharacterIndexer &ci) {
-       bool success = true;
+void RESearch::GrabMatches(CharacterIndexer &ci) {
        for (unsigned int i = 0; i < MAXTAG; i++) {
                if ((bopat[i] != NOTFOUND) && (eopat[i] != NOTFOUND)) {
                        unsigned int len = eopat[i] - bopat[i];
-                       pat[i] = new char[len + 1];
-                       if (pat[i]) {
-                               for (unsigned int j = 0; j < len; j++)
-                                       pat[i][j] = ci.CharAt(bopat[i] + j);
-                               pat[i][len] = '\0';
-                       } else {
-                               success = false;
-                       }
+                       pat[i] = std::string(len+1, '\0');
+                       for (unsigned int j = 0; j < len; j++)
+                               pat[i][j] = ci.CharAt(bopat[i] + j);
+                       pat[i][len] = '\0';
                }
        }
-       return success;
 }
 
 void RESearch::ChSet(unsigned char c) {
@@ -967,52 +958,4 @@ int RESearch::PMatch(CharacterIndexer &ci, int lp, int endp, char *ap) {
        return lp;
 }
 
-/*
- * RESearch::Substitute:
- *  substitute the matched portions of the src in dst.
- *
- *  &    substitute the entire matched pattern.
- *
- *  \digit  substitute a subpattern, with the given tag number.
- *      Tags are numbered from 1 to 9. If the particular
- *      tagged subpattern does not exist, null is substituted.
- */
-int RESearch::Substitute(CharacterIndexer &ci, char *src, char *dst) {
-       unsigned char c;
-       int  pin;
-       int bp;
-       int ep;
-
-       if (!*src || !bopat[0])
-               return 0;
-
-       while ((c = *src++) != 0) {
-               switch (c) {
-
-               case '&':
-                       pin = 0;
-                       break;
-
-               case '\\':
-                       c = *src++;
-                       if (c >= '0' && c <= '9') {
-                               pin = c - '0';
-                               break;
-                       }
-
-               default:
-                       *dst++ = c;
-                       continue;
-               }
-
-               if ((bp = bopat[pin]) != 0 && (ep = eopat[pin]) != 0) {
-                       while (ci.CharAt(bp) && bp < ep)
-                               *dst++ = ci.CharAt(bp++);
-                       if (bp < ep)
-                               return 0;
-               }
-       }
-       *dst = '\0';
-       return 1;
-}
 
diff --git a/plugins/scintilla/scintilla/src/RESearch.h b/plugins/scintilla/scintilla/src/RESearch.h
index ef8c3e1..702259d 100644
--- a/plugins/scintilla/scintilla/src/RESearch.h
+++ b/plugins/scintilla/scintilla/src/RESearch.h
@@ -33,10 +33,9 @@ class RESearch {
 public:
        RESearch(CharClassify *charClassTable);
        ~RESearch();
-       bool GrabMatches(CharacterIndexer &ci);
+       void GrabMatches(CharacterIndexer &ci);
        const char *Compile(const char *pattern, int length, bool caseSensitive, bool posix);
        int Execute(CharacterIndexer &ci, int lp, int endp);
-       int Substitute(CharacterIndexer &ci, char *src, char *dst);
 
        enum { MAXTAG=10 };
        enum { MAXNFA=2048 };
@@ -44,7 +43,7 @@ public:
 
        int bopat[MAXTAG];
        int eopat[MAXTAG];
-       char *pat[MAXTAG];
+       std::string pat[MAXTAG];
 
 private:
        void Init();
@@ -62,7 +61,7 @@ private:
        unsigned char bittab[BITBLK]; /* bit table for CCL pre-set bits */
        int failure;
        CharClassify *charClass;
-       bool iswordc(unsigned char x) {
+       bool iswordc(unsigned char x) const {
                return charClass->IsWord(x);
        }
 };
diff --git a/plugins/scintilla/scintilla/src/RunStyles.cxx b/plugins/scintilla/scintilla/src/RunStyles.cxx
index 9c4e90a..fdcfc2b 100644
--- a/plugins/scintilla/scintilla/src/RunStyles.cxx
+++ b/plugins/scintilla/scintilla/src/RunStyles.cxx
@@ -9,6 +9,8 @@
 #include <stdlib.h>
 #include <stdarg.h>
 
+#include <stdexcept>
+
 #include "Platform.h"
 
 #include "Scintilla.h"
@@ -85,7 +87,7 @@ int RunStyles::ValueAt(int position) const {
        return styles->ValueAt(starts->PartitionFromPosition(position));
 }
 
-int RunStyles::FindNextChange(int position, int end) {
+int RunStyles::FindNextChange(int position, int end) const {
        int run = starts->PartitionFromPosition(position);
        if (run < starts->Partitions()) {
                int runChange = starts->PositionFromPartition(run);
@@ -104,16 +106,22 @@ int RunStyles::FindNextChange(int position, int end) {
        }
 }
 
-int RunStyles::StartRun(int position) {
+int RunStyles::StartRun(int position) const {
        return starts->PositionFromPartition(starts->PartitionFromPosition(position));
 }
 
-int RunStyles::EndRun(int position) {
+int RunStyles::EndRun(int position) const {
        return starts->PositionFromPartition(starts->PartitionFromPosition(position) + 1);
 }
 
 bool RunStyles::FillRange(int &position, int value, int &fillLength) {
+       if (fillLength <= 0) {
+               return false;
+       }
        int end = position + fillLength;
+       if (end > Length()) {
+               return false;
+       }
        int runEnd = RunFromPosition(end);
        if (styles->ValueAt(runEnd) == value) {
                // End already has value so trim range.
@@ -249,3 +257,31 @@ int RunStyles::Find(int value, int start) const {
        }
        return -1;
 }
+
+void RunStyles::Check() const {
+       if (Length() < 0) {
+               throw std::runtime_error("RunStyles: Length can not be negative.");
+       }
+       if (starts->Partitions() < 1) {
+               throw std::runtime_error("RunStyles: Must always have 1 or more partitions.");
+       }
+       if (starts->Partitions() != styles->Length()-1) {
+               throw std::runtime_error("RunStyles: Partitions and styles different lengths.");
+       }
+       int start=0;
+       while (start < Length()) {
+               int end = EndRun(start);
+               if (start >= end) {
+                       throw std::runtime_error("RunStyles: Partition is 0 length.");
+               }
+               start = end;
+       }
+       if (styles->ValueAt(styles->Length()-1) != 0) {
+               throw std::runtime_error("RunStyles: Unused style at end changed.");
+       }
+       for (int j=1; j<styles->Length()-1; j++) {
+               if (styles->ValueAt(j) == styles->ValueAt(j-1)) {
+                       throw std::runtime_error("RunStyles: Style of a partition same as previous.");
+               }
+       }
+}
diff --git a/plugins/scintilla/scintilla/src/RunStyles.h b/plugins/scintilla/scintilla/src/RunStyles.h
index 4e90969..b096ad8 100644
--- a/plugins/scintilla/scintilla/src/RunStyles.h
+++ b/plugins/scintilla/scintilla/src/RunStyles.h
@@ -30,9 +30,9 @@ public:
        ~RunStyles();
        int Length() const;
        int ValueAt(int position) const;
-       int FindNextChange(int position, int end);
-       int StartRun(int position);
-       int EndRun(int position);
+       int FindNextChange(int position, int end) const;
+       int StartRun(int position) const;
+       int EndRun(int position) const;
        // Returns true if some values may have changed
        bool FillRange(int &position, int value, int &fillLength);
        void SetValueAt(int position, int value);
@@ -43,6 +43,8 @@ public:
        bool AllSame() const;
        bool AllSameAs(int value) const;
        int Find(int value, int start) const;
+
+       void Check() const;
 };
 
 #ifdef SCI_NAMESPACE
diff --git a/plugins/scintilla/scintilla/src/ScintillaBase.cxx 
b/plugins/scintilla/scintilla/src/ScintillaBase.cxx
index 4a0146f..0576879 100644
--- a/plugins/scintilla/scintilla/src/ScintillaBase.cxx
+++ b/plugins/scintilla/scintilla/src/ScintillaBase.cxx
@@ -14,6 +14,7 @@
 #include <string>
 #include <vector>
 #include <map>
+#include <algorithm>
 
 #include "Platform.h"
 
@@ -41,6 +42,7 @@
 #include "AutoComplete.h"
 #include "CharClassify.h"
 #include "Decoration.h"
+#include "CaseFolder.h"
 #include "Document.h"
 #include "Selection.h"
 #include "PositionCache.h"
@@ -193,6 +195,13 @@ void ScintillaBase::AutoCompleteDoubleClick(void *p) {
        sci->AutoCompleteCompleted();
 }
 
+void ScintillaBase::AutoCompleteInsert(Position startPos, int removeLen, const char *text, int textLen) {
+       UndoGroup ug(pdoc);
+       pdoc->DeleteChars(startPos, removeLen);
+       pdoc->InsertString(startPos, text, textLen);
+       SetEmptySelection(startPos + textLen);
+}
+
 void ScintillaBase::AutoCompleteStart(int lenEntered, const char *list) {
        //Platform::DebugPrintf("AutoComplete %s\n", list);
        ct.CallTipCancel();
@@ -202,17 +211,11 @@ void ScintillaBase::AutoCompleteStart(int lenEntered, const char *list) {
                        const char *typeSep = strchr(list, ac.GetTypesep());
                        int lenInsert = typeSep ? 
                                static_cast<int>(typeSep-list) : static_cast<int>(strlen(list));
-                       UndoGroup ug(pdoc);
                        if (ac.ignoreCase) {
-                               SetEmptySelection(sel.MainCaret() - lenEntered);
-                               pdoc->DeleteChars(sel.MainCaret(), lenEntered);
-                               SetEmptySelection(sel.MainCaret());
-                               pdoc->InsertString(sel.MainCaret(), list, lenInsert);
-                               SetEmptySelection(sel.MainCaret() + lenInsert);
+                               // May need to convert the case before invocation, so remove lenEntered 
characters
+                               AutoCompleteInsert(sel.MainCaret() - lenEntered, lenEntered, list, lenInsert);
                        } else {
-                               SetEmptySelection(sel.MainCaret());
-                               pdoc->InsertString(sel.MainCaret(), list + lenEntered, lenInsert - 
lenEntered);
-                               SetEmptySelection(sel.MainCaret() + lenInsert - lenEntered);
+                               AutoCompleteInsert(sel.MainCaret(), 0, list + lenEntered, lenInsert - 
lenEntered);
                        }
                        ac.Cancel();
                        return;
@@ -234,6 +237,11 @@ void ScintillaBase::AutoCompleteStart(int lenEntered, const char *list) {
                Redraw();
                pt = PointMainCaret();
        }
+       if (wMargin.GetID()) {
+               Point ptOrigin = GetVisibleOriginInMain();
+               pt.x += ptOrigin.x;
+               pt.y += ptOrigin.y;
+       }
        PRectangle rcac;
        rcac.left = pt.x - ac.lb->CaretFromEdge();
        if (pt.y >= rcPopupBounds.bottom - heightLB &&  // Wont fit below.
@@ -357,25 +365,17 @@ void ScintillaBase::AutoCompleteCompleted() {
                endPos = pdoc->ExtendWordSelect(endPos, 1, true);
        if (endPos < firstPos)
                return;
-       UndoGroup ug(pdoc);
-       if (endPos != firstPos) {
-               pdoc->DeleteChars(firstPos, endPos - firstPos);
-       }
-       SetEmptySelection(ac.posStart);
-       if (item != -1) {
-               pdoc->InsertCString(firstPos, selected.c_str());
-               SetEmptySelection(firstPos + static_cast<int>(selected.length()));
-       }
+       AutoCompleteInsert(firstPos, endPos - firstPos, selected.c_str(), 
static_cast<int>(selected.length()));
        SetLastXChosen();
 }
 
-int ScintillaBase::AutoCompleteGetCurrent() {
+int ScintillaBase::AutoCompleteGetCurrent() const {
        if (!ac.Active())
                return -1;
        return ac.GetSelection();
 }
 
-int ScintillaBase::AutoCompleteGetCurrentText(char *buffer) {
+int ScintillaBase::AutoCompleteGetCurrentText(char *buffer) const {
        if (ac.Active()) {
                int item = ac.GetSelection();
                if (item != -1) {
@@ -399,6 +399,11 @@ void ScintillaBase::CallTipShow(Point pt, const char *defn) {
        if (ct.UseStyleCallTip()) {
                ct.SetForeBack(vs.styles[STYLE_CALLTIP].fore, vs.styles[STYLE_CALLTIP].back);
        }
+       if (wMargin.GetID()) {
+               Point ptOrigin = GetVisibleOriginInMain();
+               pt.x += ptOrigin.x;
+               pt.y += ptOrigin.y;
+       }
        PRectangle rc = ct.CallTipStart(sel.MainCaret(), pt,
                vs.lineHeight,
                defn,
@@ -794,6 +799,13 @@ sptr_t ScintillaBase::WndProc(unsigned int iMessage, uptr_t wParam, sptr_t lPara
        case SCI_AUTOCGETCASEINSENSITIVEBEHAVIOUR:
                return ac.ignoreCaseBehaviour;
 
+       case SCI_AUTOCSETORDER:
+               ac.autoSort = wParam;
+               break;
+
+       case SCI_AUTOCGETORDER:
+               return ac.autoSort;
+
        case SCI_USERLISTSHOW:
                listType = wParam;
                AutoCompleteStart(0, reinterpret_cast<const char *>(lParam));
diff --git a/plugins/scintilla/scintilla/src/ScintillaBase.h b/plugins/scintilla/scintilla/src/ScintillaBase.h
index e143f02..9576139 100644
--- a/plugins/scintilla/scintilla/src/ScintillaBase.h
+++ b/plugins/scintilla/scintilla/src/ScintillaBase.h
@@ -64,11 +64,12 @@ protected:
        virtual void CancelModes();
        virtual int KeyCommand(unsigned int iMessage);
 
+       void AutoCompleteInsert(Position startPos, int removeLen, const char *text, int textLen);
        void AutoCompleteStart(int lenEntered, const char *list);
        void AutoCompleteCancel();
        void AutoCompleteMove(int delta);
-       int AutoCompleteGetCurrent();
-       int AutoCompleteGetCurrentText(char *buffer);
+       int AutoCompleteGetCurrent() const;
+       int AutoCompleteGetCurrentText(char *buffer) const;
        void AutoCompleteCharacterAdded(char ch);
        void AutoCompleteCharacterDeleted();
        void AutoCompleteCompleted();
diff --git a/plugins/scintilla/scintilla/src/Selection.cxx b/plugins/scintilla/scintilla/src/Selection.cxx
index 305d721..385e236 100644
--- a/plugins/scintilla/scintilla/src/Selection.cxx
+++ b/plugins/scintilla/scintilla/src/Selection.cxx
@@ -8,6 +8,7 @@
 #include <stdlib.h>
 
 #include <vector>
+#include <algorithm>
 
 #include "Platform.h"
 
@@ -20,14 +21,18 @@ using namespace Scintilla;
 #endif
 
 void SelectionPosition::MoveForInsertDelete(bool insertion, int startChange, int length) {
-       if (position == startChange) {
-               virtualSpace = 0;
-       }
        if (insertion) {
-               if (position > startChange) {
+               if (position == startChange) {
+                       int virtualLengthRemove = std::min(length, virtualSpace);
+                       virtualSpace -= virtualLengthRemove;
+                       position += virtualLengthRemove;
+               } else if (position > startChange) {
                        position += length;
                }
        } else {
+               if (position == startChange) {
+                       virtualSpace = 0;
+               }
                if (position > startChange) {
                        int endDeletion = startChange + length;
                        if (position > endDeletion) {
diff --git a/plugins/scintilla/scintilla/src/SplitVector.h b/plugins/scintilla/scintilla/src/SplitVector.h
index 0ccf6c9..502101b 100644
--- a/plugins/scintilla/scintilla/src/SplitVector.h
+++ b/plugins/scintilla/scintilla/src/SplitVector.h
@@ -174,8 +174,7 @@ public:
                        }
                        RoomFor(insertLength);
                        GapTo(position);
-                       for (int i = 0; i < insertLength; i++)
-                               body[part1Length + i] = v;
+                       std::fill(&body[part1Length], &body[part1Length + insertLength], v);
                        lengthBody += insertLength;
                        part1Length += insertLength;
                        gapLength -= insertLength;
diff --git a/plugins/scintilla/scintilla/src/Style.cxx b/plugins/scintilla/scintilla/src/Style.cxx
index 375738c..8b5b42d 100644
--- a/plugins/scintilla/scintilla/src/Style.cxx
+++ b/plugins/scintilla/scintilla/src/Style.cxx
@@ -21,7 +21,7 @@ FontAlias::FontAlias() {
 
 FontAlias::~FontAlias() {
        SetID(0);
-       // ~Font will not release the actual font resource sine it is now 0
+       // ~Font will not release the actual font resource since it is now 0
 }
 
 void FontAlias::MakeAlias(Font &fontOrigin) {
@@ -32,12 +32,29 @@ void FontAlias::ClearFont() {
        SetID(0);
 }
 
-bool FontSpecification::EqualTo(const FontSpecification &other) const {
-       return weight == other.weight &&
+bool FontSpecification::operator==(const FontSpecification &other) const {
+       return fontName == other.fontName &&
+              weight == other.weight &&
               italic == other.italic &&
               size == other.size &&
               characterSet == other.characterSet &&
-              fontName == other.fontName;
+              extraFontFlag == other.extraFontFlag;
+}
+
+bool FontSpecification::operator<(const FontSpecification &other) const {
+       if (fontName != other.fontName)
+               return fontName < other.fontName;
+       if (weight != other.weight)
+               return weight < other.weight;
+       if (italic != other.italic)
+               return italic == false;
+       if (size != other.size)
+               return size < other.size;
+       if (characterSet != other.characterSet)
+               return characterSet < other.characterSet;
+       if (extraFontFlag != other.extraFontFlag)
+               return extraFontFlag < other.extraFontFlag;
+       return false;
 }
 
 FontMeasurements::FontMeasurements() {
@@ -68,6 +85,7 @@ Style::Style(const Style &source) : FontSpecification(), FontMeasurements() {
        weight = source.weight;
        italic = source.italic;
        size = source.size;
+       fontName = source.fontName;
        eolFilled = source.eolFilled;
        underline = source.underline;
        caseForce = source.caseForce;
@@ -91,6 +109,7 @@ Style &Style::operator=(const Style &source) {
        weight = source.weight;
        italic = source.italic;
        size = source.size;
+       fontName = source.fontName;
        eolFilled = source.eolFilled;
        underline = source.underline;
        caseForce = source.caseForce;
diff --git a/plugins/scintilla/scintilla/src/Style.h b/plugins/scintilla/scintilla/src/Style.h
index 85663ac..4bd79de 100644
--- a/plugins/scintilla/scintilla/src/Style.h
+++ b/plugins/scintilla/scintilla/src/Style.h
@@ -27,7 +27,8 @@ struct FontSpecification {
                characterSet(0),
                extraFontFlag(0) {
        }
-       bool EqualTo(const FontSpecification &other) const;
+       bool operator==(const FontSpecification &other) const;
+       bool operator<(const FontSpecification &other) const;
 };
 
 // Just like Font but only has a copy of the FontID so should not delete it
@@ -77,7 +78,7 @@ public:
                   const char *fontName_, int characterSet_,
                   int weight_, bool italic_, bool eolFilled_,
                   bool underline_, ecaseForced caseForce_,
-                  bool visible_, bool changeable_, bool hotspot_);
+                  bool visible_, bool changeable_, bool hotspot_);
        void ClearTo(const Style &source);
        void Copy(Font &font_, const FontMeasurements &fm_);
        bool IsProtected() const { return !(changeable && visible);}
diff --git a/plugins/scintilla/scintilla/src/UnicodeFromUTF8.h 
b/plugins/scintilla/scintilla/src/UnicodeFromUTF8.h
new file mode 100644
index 0000000..24517e8
--- /dev/null
+++ b/plugins/scintilla/scintilla/src/UnicodeFromUTF8.h
@@ -0,0 +1,19 @@
+// Scintilla source code edit control
+/** @file UnicodeFromUTF8.h
+ ** Lexer infrastructure.
+ **/
+// Copyright 2013 by Neil Hodgson <neilh scintilla org>
+// This file is in the public domain.
+
+inline int UnicodeFromUTF8(const unsigned char *us) {
+       if (us[0] < 0xC2) {
+               return us[0];
+       } else if (us[0] < 0xE0) {
+               return ((us[0] & 0x1F) << 6) + (us[1] & 0x3F);
+       } else if (us[0] < 0xF0) {
+               return ((us[0] & 0xF) << 12) + ((us[1] & 0x3F) << 6) + (us[2] & 0x3F);
+       } else if (us[0] < 0xF5) {
+               return ((us[0] & 0x7) << 18) + ((us[1] & 0x3F) << 12) + ((us[2] & 0x3F) << 6) + (us[3] & 
0x3F);
+       }
+       return us[0];
+}
diff --git a/plugins/scintilla/scintilla/src/ViewStyle.cxx b/plugins/scintilla/scintilla/src/ViewStyle.cxx
index 9181d9b..8d2a60e 100644
--- a/plugins/scintilla/scintilla/src/ViewStyle.cxx
+++ b/plugins/scintilla/scintilla/src/ViewStyle.cxx
@@ -33,100 +33,55 @@ MarginStyle::MarginStyle() :
 
 // A list of the fontnames - avoids wasting space in each style
 FontNames::FontNames() {
-       size = 8;
-       names = new char *[size];
-       max = 0;
 }
 
 FontNames::~FontNames() {
        Clear();
-       delete []names;
-       names = 0;
 }
 
 void FontNames::Clear() {
-       for (int i=0; i<max; i++) {
-               delete []names[i];
+       for (std::vector<char *>::const_iterator it=names.begin(); it != names.end(); ++it) {
+               delete []*it;
        }
-       max = 0;
+       names.clear();
 }
 
 const char *FontNames::Save(const char *name) {
        if (!name)
                return 0;
-       for (int i=0; i<max; i++) {
-               if (strcmp(names[i], name) == 0) {
-                       return names[i];
-               }
-       }
-       if (max >= size) {
-               // Grow array
-               int sizeNew = size * 2;
-               char **namesNew = new char *[sizeNew];
-               for (int j=0; j<max; j++) {
-                       namesNew[j] = names[j];
+
+       for (std::vector<char *>::const_iterator it=names.begin(); it != names.end(); ++it) {
+               if (strcmp(*it, name) == 0) {
+                       return *it;
                }
-               delete []names;
-               names = namesNew;
-               size = sizeNew;
        }
-       names[max] = new char[strlen(name) + 1];
-       strcpy(names[max], name);
-       max++;
-       return names[max-1];
+       char *nameSave = new char[strlen(name) + 1];
+       strcpy(nameSave, name);
+       names.push_back(nameSave);
+       return nameSave;
 }
 
-FontRealised::FontRealised(const FontSpecification &fs) {
-       frNext = NULL;
-       (FontSpecification &)(*this) = fs;
+FontRealised::FontRealised() {
 }
 
 FontRealised::~FontRealised() {
        font.Release();
-       delete frNext;
-       frNext = 0;
 }
 
-void FontRealised::Realise(Surface &surface, int zoomLevel, int technology) {
-       PLATFORM_ASSERT(fontName);
-       sizeZoomed = size + zoomLevel * SC_FONT_SIZE_MULTIPLIER;
+void FontRealised::Realise(Surface &surface, int zoomLevel, int technology, const FontSpecification &fs) {
+       PLATFORM_ASSERT(fs.fontName);
+       sizeZoomed = fs.size + zoomLevel * SC_FONT_SIZE_MULTIPLIER;
        if (sizeZoomed <= 2 * SC_FONT_SIZE_MULTIPLIER)  // Hangs if sizeZoomed <= 1
                sizeZoomed = 2 * SC_FONT_SIZE_MULTIPLIER;
 
        float deviceHeight = surface.DeviceHeightFont(sizeZoomed);
-       FontParameters fp(fontName, deviceHeight / SC_FONT_SIZE_MULTIPLIER, weight, italic, extraFontFlag, 
technology, characterSet);
+       FontParameters fp(fs.fontName, deviceHeight / SC_FONT_SIZE_MULTIPLIER, fs.weight, fs.italic, 
fs.extraFontFlag, technology, fs.characterSet);
        font.Create(fp);
 
        ascent = surface.Ascent(font);
        descent = surface.Descent(font);
        aveCharWidth = surface.AverageCharWidth(font);
        spaceWidth = surface.WidthChar(font, ' ');
-       if (frNext) {
-               frNext->Realise(surface, zoomLevel, technology);
-       }
-}
-
-FontRealised *FontRealised::Find(const FontSpecification &fs) {
-       if (!fs.fontName)
-               return this;
-       FontRealised *fr = this;
-       while (fr) {
-               if (fr->EqualTo(fs))
-                       return fr;
-               fr = fr->frNext;
-       }
-       return 0;
-}
-
-void FontRealised::FindMaxAscentDescent(unsigned int &maxAscent, unsigned int &maxDescent) {
-       FontRealised *fr = this;
-       while (fr) {
-               if (maxAscent < fr->ascent)
-                       maxAscent = fr->ascent;
-               if (maxDescent < fr->descent)
-                       maxDescent = fr->descent;
-               fr = fr->frNext;
-       }
 }
 
 ViewStyle::ViewStyle() {
@@ -134,9 +89,8 @@ ViewStyle::ViewStyle() {
 }
 
 ViewStyle::ViewStyle(const ViewStyle &source) {
-       frFirst = NULL;
-       Init(source.stylesSize);
-       for (unsigned int sty=0; sty<source.stylesSize; sty++) {
+       Init(source.styles.size());
+       for (unsigned int sty=0; sty<source.styles.size(); sty++) {
                styles[sty] = source.styles[sty];
                // Can't just copy fontname as its lifetime is relative to its owning ViewStyle
                styles[sty].fontName = fontNames.Save(source.styles[sty].fontName);
@@ -218,16 +172,14 @@ ViewStyle::ViewStyle(const ViewStyle &source) {
 }
 
 ViewStyle::~ViewStyle() {
-       delete []styles;
-       styles = NULL;
-       delete frFirst;
-       frFirst = NULL;
+       styles.clear();
+       for (FontMap::iterator it = fonts.begin(); it != fonts.end(); ++it) {
+               delete it->second;
+       }
+       fonts.clear();
 }
 
 void ViewStyle::Init(size_t stylesSize_) {
-       frFirst = NULL;
-       stylesSize = 0;
-       styles = NULL;
        AllocStyles(stylesSize_);
        nextExtendedStyle = 256;
        fontNames.Clear();
@@ -334,52 +286,42 @@ void ViewStyle::Init(size_t stylesSize_) {
        braceBadLightIndicator = 0;
 }
 
-void ViewStyle::CreateFont(const FontSpecification &fs) {
-       if (fs.fontName) {
-               for (FontRealised *cur=frFirst; cur; cur=cur->frNext) {
-                       if (cur->EqualTo(fs))
-                               return;
-                       if (!cur->frNext) {
-                               cur->frNext = new FontRealised(fs);
-                               return;
-                       }
-               }
-               frFirst = new FontRealised(fs);
+void ViewStyle::Refresh(Surface &surface) {
+       for (FontMap::iterator it = fonts.begin(); it != fonts.end(); ++it) {
+               delete it->second;
        }
-}
+       fonts.clear();
 
-void ViewStyle::Refresh(Surface &surface) {
-       delete frFirst;
-       frFirst = NULL;
        selbar = Platform::Chrome();
        selbarlight = Platform::ChromeHighlight();
 
-       for (unsigned int i=0; i<stylesSize; i++) {
+       for (unsigned int i=0; i<styles.size(); i++) {
                styles[i].extraFontFlag = extraFontFlag;
        }
 
        CreateFont(styles[STYLE_DEFAULT]);
-       for (unsigned int j=0; j<stylesSize; j++) {
+       for (unsigned int j=0; j<styles.size(); j++) {
                CreateFont(styles[j]);
        }
 
-       assert(frFirst);
-       frFirst->Realise(surface, zoomLevel, technology);
+       for (FontMap::iterator it = fonts.begin(); it != fonts.end(); ++it) {
+               it->second->Realise(surface, zoomLevel, technology, it->first);
+       }
 
-       for (unsigned int k=0; k<stylesSize; k++) {
-               FontRealised *fr = frFirst->Find(styles[k]);
+       for (unsigned int k=0; k<styles.size(); k++) {
+               FontRealised *fr = Find(styles[k]);
                styles[k].Copy(fr->font, *fr);
        }
        maxAscent = 1;
        maxDescent = 1;
-       frFirst->FindMaxAscentDescent(maxAscent, maxDescent);
+       FindMaxAscentDescent(maxAscent, maxDescent);
        maxAscent += extraAscent;
        maxDescent += extraDescent;
        lineHeight = maxAscent + maxDescent;
 
        someStylesProtected = false;
        someStylesForceCase = false;
-       for (unsigned int l=0; l<stylesSize; l++) {
+       for (unsigned int l=0; l<styles.size(); l++) {
                if (styles[l].IsProtected()) {
                        someStylesProtected = true;
                }
@@ -401,25 +343,6 @@ void ViewStyle::Refresh(Surface &surface) {
        textStart = marginInside ? fixedColumnWidth : leftMarginWidth;
 }
 
-void ViewStyle::AllocStyles(size_t sizeNew) {
-       Style *stylesNew = new Style[sizeNew];
-       size_t i=0;
-       for (; i<stylesSize; i++) {
-               stylesNew[i] = styles[i];
-               stylesNew[i].fontName = styles[i].fontName;
-       }
-       if (stylesSize > STYLE_DEFAULT) {
-               for (; i<sizeNew; i++) {
-                       if (i != STYLE_DEFAULT) {
-                               stylesNew[i].ClearTo(styles[STYLE_DEFAULT]);
-                       }
-               }
-       }
-       delete []styles;
-       styles = stylesNew;
-       stylesSize = sizeNew;
-}
-
 void ViewStyle::ReleaseAllExtendedStyles() {
        nextExtendedStyle = 256;
 }
@@ -431,11 +354,8 @@ int ViewStyle::AllocateExtendedStyles(int numberStyles) {
 }
 
 void ViewStyle::EnsureStyle(size_t index) {
-       if (index >= stylesSize) {
-               size_t sizeNew = stylesSize * 2;
-               while (sizeNew <= index)
-                       sizeNew *= 2;
-               AllocStyles(sizeNew);
+       if (index >= styles.size()) {
+               AllocStyles(index+1);
        }
 }
 
@@ -449,7 +369,7 @@ void ViewStyle::ResetDefaultStyle() {
 
 void ViewStyle::ClearStyles() {
        // Reset all styles to be like the default style
-       for (unsigned int i=0; i<stylesSize; i++) {
+       for (unsigned int i=0; i<styles.size(); i++) {
                if (i != STYLE_DEFAULT) {
                        styles[i].ClearTo(styles[STYLE_DEFAULT]);
                }
@@ -470,7 +390,7 @@ bool ViewStyle::ProtectionActive() const {
 }
 
 bool ViewStyle::ValidStyle(size_t styleIndex) const {
-       return styleIndex < stylesSize;
+       return styleIndex < styles.size();
 }
 
 void ViewStyle::CalcLargestMarkerHeight() {
@@ -478,13 +398,54 @@ void ViewStyle::CalcLargestMarkerHeight() {
        for (int m = 0; m <= MARKER_MAX; ++m) {
                switch (markers[m].markType) {
                case SC_MARK_PIXMAP:
-                       if (markers[m].pxpm->GetHeight() > largestMarkerHeight)
+                       if (markers[m].pxpm && markers[m].pxpm->GetHeight() > largestMarkerHeight)
                                largestMarkerHeight = markers[m].pxpm->GetHeight();
                        break;
                case SC_MARK_RGBAIMAGE:
-                       if (markers[m].image->GetHeight() > largestMarkerHeight)
+                       if (markers[m].image && markers[m].image->GetHeight() > largestMarkerHeight)
                                largestMarkerHeight = markers[m].image->GetHeight();
                        break;
                }
        }
 }
+
+void ViewStyle::AllocStyles(size_t sizeNew) {
+       size_t i=styles.size();
+       styles.resize(sizeNew);
+       if (styles.size() > STYLE_DEFAULT) {
+               for (; i<sizeNew; i++) {
+                       if (i != STYLE_DEFAULT) {
+                               styles[i].ClearTo(styles[STYLE_DEFAULT]);
+                       }
+               }
+       }
+}
+
+void ViewStyle::CreateFont(const FontSpecification &fs) {
+       if (fs.fontName) {
+               FontMap::iterator it = fonts.find(fs);
+               if (it == fonts.end()) {
+                       fonts[fs] = new FontRealised();
+               }
+       }
+}
+
+FontRealised *ViewStyle::Find(const FontSpecification &fs) {
+       if (!fs.fontName)       // Invalid specification so return arbitrary object
+               return fonts.begin()->second;
+       FontMap::iterator it = fonts.find(fs);
+       if (it != fonts.end()) {
+               // Should always reach here since map was just set for all styles
+               return it->second;
+       }
+       return 0;
+}
+
+void ViewStyle::FindMaxAscentDescent(unsigned int &maxAscent, unsigned int &maxDescent) {
+       for (FontMap::const_iterator it = fonts.begin(); it != fonts.end(); ++it) {
+               if (maxAscent < it->second->ascent)
+                       maxAscent = it->second->ascent;
+               if (maxDescent < it->second->descent)
+                       maxDescent = it->second->descent;
+       }
+}
diff --git a/plugins/scintilla/scintilla/src/ViewStyle.h b/plugins/scintilla/scintilla/src/ViewStyle.h
index bd26613..5593c0b 100644
--- a/plugins/scintilla/scintilla/src/ViewStyle.h
+++ b/plugins/scintilla/scintilla/src/ViewStyle.h
@@ -28,9 +28,7 @@ public:
  */
 class FontNames {
 private:
-       char **names;
-       int size;
-       int max;
+       std::vector<char *> names;
 
        // Private so FontNames objects can not be copied
        FontNames(const FontNames &);
@@ -41,32 +39,30 @@ public:
        const char *Save(const char *name);
 };
 
-class FontRealised : public FontSpecification, public FontMeasurements {
+class FontRealised : public FontMeasurements {
        // Private so FontRealised objects can not be copied
        FontRealised(const FontRealised &);
        FontRealised &operator=(const FontRealised &);
 public:
        Font font;
-       FontRealised *frNext;
-       FontRealised(const FontSpecification &fs);
+       FontRealised();
        virtual ~FontRealised();
-       void Realise(Surface &surface, int zoomLevel, int technology);
-       FontRealised *Find(const FontSpecification &fs);
-       void FindMaxAscentDescent(unsigned int &maxAscent, unsigned int &maxDescent);
+       void Realise(Surface &surface, int zoomLevel, int technology, const FontSpecification &fs);
 };
 
 enum IndentView {ivNone, ivReal, ivLookForward, ivLookBoth};
 
 enum WhiteSpaceVisibility {wsInvisible=0, wsVisibleAlways=1, wsVisibleAfterIndent=2};
 
+typedef std::map<FontSpecification, FontRealised *> FontMap;
+
 /**
  */
 class ViewStyle {
-public:
        FontNames fontNames;
-       FontRealised *frFirst;
-       size_t stylesSize;
-       Style *styles;
+       FontMap fonts;
+public:
+       std::vector<Style> styles;
        size_t nextExtendedStyle;
        LineMarker markers[MARKER_MAX + 1];
        int largestMarkerHeight;
@@ -143,9 +139,7 @@ public:
        ViewStyle(const ViewStyle &source);
        ~ViewStyle();
        void Init(size_t stylesSize_=64);
-       void CreateFont(const FontSpecification &fs);
        void Refresh(Surface &surface);
-       void AllocStyles(size_t sizeNew);
        void ReleaseAllExtendedStyles();
        int AllocateExtendedStyles(int numberStyles);
        void EnsureStyle(size_t index);
@@ -155,6 +149,13 @@ public:
        bool ProtectionActive() const;
        bool ValidStyle(size_t styleIndex) const;
        void CalcLargestMarkerHeight();
+private:
+       void AllocStyles(size_t sizeNew);
+       void CreateFont(const FontSpecification &fs);
+       FontRealised *Find(const FontSpecification &fs);
+       void FindMaxAscentDescent(unsigned int &maxAscent, unsigned int &maxDescent);
+       // Private so can only be copied through copy constructor which ensures font names initialised 
correctly
+       ViewStyle &operator=(const ViewStyle &);
 };
 
 #ifdef SCI_NAMESPACE
diff --git a/plugins/scintilla/scintilla/src/XPM.cxx b/plugins/scintilla/scintilla/src/XPM.cxx
index 7188c24..d6397af 100644
--- a/plugins/scintilla/scintilla/src/XPM.cxx
+++ b/plugins/scintilla/scintilla/src/XPM.cxx
@@ -41,12 +41,8 @@ static size_t MeasureLength(const char *s) {
        return i;
 }
 
-ColourDesired XPM::ColourDesiredFromCode(int ch) const {
-       return *colourCodeTable[ch];
-}
-
 ColourDesired XPM::ColourFromCode(int ch) const {
-       return *colourCodeTable[ch];
+       return colourCodeTable[ch];
 }
 
 void XPM::FillRun(Surface *surface, int code, int startX, int y, int x) {
@@ -56,13 +52,11 @@ void XPM::FillRun(Surface *surface, int code, int startX, int y, int x) {
        }
 }
 
-XPM::XPM(const char *textForm) :
-       data(0), codes(0), colours(0), lines(0) {
+XPM::XPM(const char *textForm) {
        Init(textForm);
 }
 
-XPM::XPM(const char *const *linesForm) :
-       data(0), codes(0), colours(0), lines(0) {
+XPM::XPM(const char *const *linesForm) {
        Init(linesForm);
 }
 
@@ -76,10 +70,9 @@ void XPM::Init(const char *textForm) {
        // if memcmp implemented strangely. Must be 4 bytes at least at destination.
        if ((0 == memcmp(textForm, "/* X", 4)) && (0 == memcmp(textForm, "/* XPM */", 9))) {
                // Build the lines form out of the text form
-               const char **linesForm = LinesFormFromTextForm(textForm);
-               if (linesForm != 0) {
-                       Init(linesForm);
-                       delete []linesForm;
+               std::vector<const char *> linesForm = LinesFormFromTextForm(textForm);
+               if (!linesForm.empty()) {
+                       Init(&linesForm[0]);
                }
        } else {
                // It is really in line form
@@ -92,18 +85,17 @@ void XPM::Init(const char *const *linesForm) {
        height = 1;
        width = 1;
        nColours = 1;
-       data = NULL;
+       pixels.clear();
        codeTransparent = ' ';
-       codes = NULL;
-       colours = NULL;
-       lines = NULL;
        if (!linesForm)
                return;
 
+       std::fill(colourCodeTable, colourCodeTable+256, 0);
        const char *line0 = linesForm[0];
        width = atoi(line0);
        line0 = NextField(line0);
        height = atoi(line0);
+       pixels.resize(width*height);
        line0 = NextField(line0);
        nColours = atoi(line0);
        line0 = NextField(line0);
@@ -111,56 +103,33 @@ void XPM::Init(const char *const *linesForm) {
                // Only one char per pixel is supported
                return;
        }
-       codes = new char[nColours];
-       colours = new ColourDesired[nColours];
-
-       int strings = 1+height+nColours;
-       lines = new char *[strings];
-       size_t allocation = 0;
-       for (int i=0; i<strings; i++) {
-               allocation += MeasureLength(linesForm[i]) + 1;
-       }
-       data = new char[allocation];
-       char *nextBit = data;
-       for (int j=0; j<strings; j++) {
-               lines[j] = nextBit;
-               size_t len = MeasureLength(linesForm[j]);
-               memcpy(nextBit, linesForm[j], len);
-               nextBit += len;
-               *nextBit++ = '\0';
-       }
-
-       for (int code=0; code<256; code++) {
-               colourCodeTable[code] = 0;
-       }
 
        for (int c=0; c<nColours; c++) {
                const char *colourDef = linesForm[c+1];
-               codes[c] = colourDef[0];
+               int code = static_cast<unsigned char>(colourDef[0]);
                colourDef += 4;
+               ColourDesired colour(0xff, 0xff, 0xff);
                if (*colourDef == '#') {
-                       colours[c].Set(colourDef);
+                       colour.Set(colourDef);
                } else {
-                       colours[c] = ColourDesired(0xff, 0xff, 0xff);
-                       codeTransparent = codes[c];
+                       codeTransparent = code;
                }
-               colourCodeTable[static_cast<unsigned char>(codes[c])] = &(colours[c]);
+               colourCodeTable[code] = colour;
+       }
+
+       for (int y=0; y<height; y++) {
+               const char *lform = linesForm[y+nColours+1];
+               size_t len = MeasureLength(lform);
+               for (size_t x = 0; x<len; x++) 
+                       pixels[y * width + x] = static_cast<unsigned char>(lform[x]);
        }
 }
 
 void XPM::Clear() {
-       delete []data;
-       data = 0;
-       delete []codes;
-       codes = 0;
-       delete []colours;
-       colours = 0;
-       delete []lines;
-       lines = 0;
 }
 
 void XPM::Draw(Surface *surface, PRectangle &rc) {
-       if (!data || !codes || !colours || !lines) {
+       if (pixels.empty()) {
                return;
        }
        // Centre the pixmap
@@ -170,7 +139,7 @@ void XPM::Draw(Surface *surface, PRectangle &rc) {
                int prevCode = 0;
                int xStartRun = 0;
                for (int x=0; x<width; x++) {
-                       int code = lines[y+nColours+1][x];
+                       int code = pixels[y * width + x];
                        if (code != prevCode) {
                                FillRun(surface, prevCode, startX + xStartRun, startY + y, startX + x);
                                xStartRun = x;
@@ -182,23 +151,23 @@ void XPM::Draw(Surface *surface, PRectangle &rc) {
 }
 
 void XPM::PixelAt(int x, int y, ColourDesired &colour, bool &transparent) const {
-       if (!data || !codes || !colours || !lines || (x<0) || (x >= width) || (y<0) || (y >= height)) {
+       if (pixels.empty() || (x<0) || (x >= width) || (y<0) || (y >= height)) {
                colour = 0;
                transparent = true;
                return;
        }
-       int code = lines[y+nColours+1][x];
+       int code = pixels[y * width + x];
        transparent = code == codeTransparent;
        if (transparent) {
                colour = 0;
        } else {
-               colour = ColourDesiredFromCode(code).AsLong();
+               colour = ColourFromCode(code).AsLong();
        }
 }
 
-const char **XPM::LinesFormFromTextForm(const char *textForm) {
+std::vector<const char *> XPM::LinesFormFromTextForm(const char *textForm) {
        // Build the lines form out of the text form
-       const char **linesForm = 0;
+       std::vector<const char *> linesForm;
        int countQuotes = 0;
        int strings=1;
        int j=0;
@@ -214,111 +183,23 @@ const char **XPM::LinesFormFromTextForm(const char *textForm) {
                                line0 = NextField(line0);
                                // Add 1 line for each colour
                                strings += atoi(line0);
-                               linesForm = new const char *[strings];
-                               if (linesForm == 0) {
-                                       break;  // Memory error!
-                               }
                        }
                        if (countQuotes / 2 >= strings) {
                                break;  // Bad height or number of colors!
                        }
                        if ((countQuotes & 1) == 0) {
-                               linesForm[countQuotes / 2] = textForm + j + 1;
+                               linesForm.push_back(textForm + j + 1);
                        }
                        countQuotes++;
                }
        }
        if (textForm[j] == '\0' || countQuotes / 2 > strings) {
                // Malformed XPM! Height + number of colors too high or too low
-               delete []linesForm;
-               linesForm = 0;
+               linesForm.clear();
        }
        return linesForm;
 }
 
-// In future, may want to minimize search time by sorting and using a binary search.
-
-XPMSet::XPMSet() : set(0), len(0), maximum(0), height(-1), width(-1) {
-}
-
-XPMSet::~XPMSet() {
-       Clear();
-}
-
-void XPMSet::Clear() {
-       for (int i = 0; i < len; i++) {
-               delete set[i];
-       }
-       delete []set;
-       set = 0;
-       len = 0;
-       maximum = 0;
-       height = -1;
-       width = -1;
-}
-
-void XPMSet::Add(int ident, const char *textForm) {
-       // Invalidate cached dimensions
-       height = -1;
-       width = -1;
-
-       // Replace if this id already present
-       for (int i = 0; i < len; i++) {
-               if (set[i]->GetId() == ident) {
-                       set[i]->Init(textForm);
-                       return;
-               }
-       }
-
-       // Not present, so add to end
-       XPM *pxpm = new XPM(textForm);
-       if (pxpm) {
-               pxpm->SetId(ident);
-               if (len == maximum) {
-                       maximum += 64;
-                       XPM **setNew = new XPM *[maximum];
-                       for (int i = 0; i < len; i++) {
-                               setNew[i] = set[i];
-                       }
-                       delete []set;
-                       set = setNew;
-               }
-               set[len] = pxpm;
-               len++;
-       }
-}
-
-XPM *XPMSet::Get(int ident) {
-       for (int i = 0; i < len; i++) {
-               if (set[i]->GetId() == ident) {
-                       return set[i];
-               }
-       }
-       return 0;
-}
-
-int XPMSet::GetHeight() {
-       if (height < 0) {
-               for (int i = 0; i < len; i++) {
-                       if (height < set[i]->GetHeight()) {
-                               height = set[i]->GetHeight();
-                       }
-               }
-       }
-       return (height > 0) ? height : 0;
-}
-
-int XPMSet::GetWidth() {
-       if (width < 0) {
-               for (int i = 0; i < len; i++) {
-                       if (width < set[i]->GetWidth()) {
-                               width = set[i]->GetWidth();
-                       }
-               }
-       }
-       return (width > 0) ? width : 0;
-}
-
 RGBAImage::RGBAImage(int width_, int height_, float scale_, const unsigned char *pixels_) :
        height(height_), width(width_), scale(scale_) {
        if (pixels_) {
diff --git a/plugins/scintilla/scintilla/src/XPM.h b/plugins/scintilla/scintilla/src/XPM.h
index e047ca8..c19025d 100644
--- a/plugins/scintilla/scintilla/src/XPM.h
+++ b/plugins/scintilla/scintilla/src/XPM.h
@@ -1,6 +1,6 @@
 // Scintilla source code edit control
 /** @file XPM.h
- ** Define a class that holds data in the X Pixmap (XPM) format.
+ ** Define a classes to hold image data in the X Pixmap (XPM) and RGBA formats.
  **/
 // Copyright 1998-2003 by Neil Hodgson <neilh scintilla org>
 // The License.txt file describes the conditions under which this software may be distributed.
@@ -16,19 +16,14 @@ namespace Scintilla {
  * Hold a pixmap in XPM format.
  */
 class XPM {
-       int pid;                // Assigned by container
        int height;
        int width;
        int nColours;
-       char *data;
+       std::vector<unsigned char> pixels;
+       ColourDesired colourCodeTable[256];
        char codeTransparent;
-       char *codes;
-       ColourDesired *colours;
-       ColourDesired ColourDesiredFromCode(int ch) const;
        ColourDesired ColourFromCode(int ch) const;
        void FillRun(Surface *surface, int code, int startX, int y, int x);
-       char **lines;
-       ColourDesired *colourCodeTable[256];
 public:
        XPM(const char *textForm);
        XPM(const char *const *linesForm);
@@ -38,41 +33,15 @@ public:
        void Clear();
        /// Decompose image into runs and use FillRectangle for each run
        void Draw(Surface *surface, PRectangle &rc);
-       char **InLinesForm() { return lines; }
-       void SetId(int pid_) { pid = pid_; }
-       int GetId() const { return pid; }
        int GetHeight() const { return height; }
        int GetWidth() const { return width; }
        void PixelAt(int x, int y, ColourDesired &colour, bool &transparent) const;
-       static const char **LinesFormFromTextForm(const char *textForm);
+private:
+       static std::vector<const char *>LinesFormFromTextForm(const char *textForm);
 };
 
 /**
- * A collection of pixmaps indexed by integer id.
- */
-class XPMSet {
-       XPM **set;      ///< The stored XPMs.
-       int len;        ///< Current number of XPMs.
-       int maximum;    ///< Current maximum number of XPMs, increased by steps if reached.
-       int height;     ///< Memorize largest height of the set.
-       int width;      ///< Memorize largest width of the set.
-public:
-       XPMSet();
-       ~XPMSet();
-       /// Remove all XPMs.
-       void Clear();
-       /// Add a XPM.
-       void Add(int ident, const char *textForm);
-       /// Get XPM by id.
-       XPM *Get(int ident);
-       /// Give the largest height of the set.
-       int GetHeight();
-       /// Give the largest width of the set.
-       int GetWidth();
-};
-
-/**
- * An translucent image stoed as a sequence of RGBA bytes.
+ * A translucent image stored as a sequence of RGBA bytes.
  */
 class RGBAImage {
        // Private so RGBAImage objects can not be copied


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]