From cd503a34bbcee281b8a214517b56b86fb23f492b Mon Sep 17 00:00:00 2001 From: cxl Date: Mon, 22 Jun 2020 06:38:59 +0000 Subject: [PATCH] Core: Fixed memory info in FreeBSD, ide: Refactoring CodeBase git-svn-id: svn://ultimatepp.org/upp/trunk@14617 f0d560ea-af0d-0410-9eb7-867de7ffcac7 --- uppsrc/Core/Cpu.cpp | 6 +- uppsrc/Core/Vcont.h | 2 +- uppsrc/CppBase/Base.cpp | 6 + uppsrc/CppBase/CppBase.h | 8 +- uppsrc/CppBase/CppBase.upp | 1 + uppsrc/CppBase/Internal.h | 4 +- uppsrc/CppBase/Parser.cpp | 3 +- uppsrc/CppBase/Pre.cpp | 13 +- uppsrc/CppBase/Qualify.cpp | 2 +- uppsrc/CppBase/ScopeInfo.cpp | 2 +- uppsrc/CppBase/cpp.cpp | 2 +- uppsrc/CppBase/cpplex.cpp | 9 +- uppsrc/CppBase/ppfile.cpp | 262 +++++++++++++++-------------- uppsrc/CppBase/srcfiles.cpp | 10 +- uppsrc/CppBase/util.cpp | 94 +++++++++++ uppsrc/CtrlLib/Progress.cpp | 2 + uppsrc/ide/About.cpp | 1 + uppsrc/ide/Annotations.cpp | 1 + uppsrc/ide/Assist.cpp | 1 + uppsrc/ide/Browser/Base.cpp | 89 ++++++---- uppsrc/ide/Browser/Browser.h | 1 + uppsrc/ide/Browser/CodeBrowser.cpp | 3 + uppsrc/ide/Browser/CodeRef.cpp | 2 + uppsrc/ide/Browser/Util.cpp | 1 + uppsrc/ide/ContextGoto.cpp | 2 + uppsrc/ide/Navigator.cpp | 3 + uppsrc/ide/Swaps.cpp | 1 + uppsrc/ide/Thisbacks.cpp | 2 + uppsrc/ide/UppDlg.h | 2 +- uppsrc/ide/Virtuals.cpp | 1 + uppsrc/ide/idefile.cpp | 2 +- 31 files changed, 351 insertions(+), 187 deletions(-) create mode 100644 uppsrc/CppBase/util.cpp diff --git a/uppsrc/Core/Cpu.cpp b/uppsrc/Core/Cpu.cpp index a75ff9bba..97c20d3b4 100644 --- a/uppsrc/Core/Cpu.cpp +++ b/uppsrc/Core/Cpu.cpp @@ -181,7 +181,7 @@ void GetSystemMemoryStatus(uint64& total, uint64& available) } #endif #ifdef PLATFORM_FREEBSD - int64 page_size; + u_int page_size; struct vmtotal vmt; size_t vmt_size, uint_size; @@ -190,8 +190,8 @@ void GetSystemMemoryStatus(uint64& total, uint64& available) if(sysctlbyname("vm.vmtotal", &vmt, &vmt_size, NULL, 0) >= 0 && sysctlbyname("vm.stats.vm.v_page_size", &page_size, &uint_size, NULL, 0) >= 0) { - available = vmt.t_free * page_size; - total = vmt.t_avm * page_size; + available = vmt.t_free * (u_int64_t)page_size; + total = vmt.t_avm * (u_int64_t)page_size; return; } #endif diff --git a/uppsrc/Core/Vcont.h b/uppsrc/Core/Vcont.h index da501f70b..69c560337 100644 --- a/uppsrc/Core/Vcont.h +++ b/uppsrc/Core/Vcont.h @@ -325,7 +325,7 @@ public: void Insert(int i, const Array& x, int offset, int count); template void InsertRange(int i, const Range& r); - void Insert(int i, Array&& x) { vector.InsertPick(i, pick(x.vector)); } + void Insert(int i, Array&& x) { vector.Insert(i, pick(x.vector)); } void Append(const Array& x) { Insert(GetCount(), x); } void Append(const Array& x, int o, int c) { Insert(GetCount(), x, o, c); } void Append(Array&& x) { InsertPick(GetCount(), pick(x)); } diff --git a/uppsrc/CppBase/Base.cpp b/uppsrc/CppBase/Base.cpp index c3fd8dc2d..ff5b262e2 100644 --- a/uppsrc/CppBase/Base.cpp +++ b/uppsrc/CppBase/Base.cpp @@ -86,6 +86,12 @@ void CppBase::Sweep(const Index& file, bool keep) Remove(remove); } +void CppBase::Append(CppBase&& base) +{ + for(int i = 0; i < base.GetCount(); i++) + GetAdd(base.GetKey(i)).Append(pick(base[i])); +} + void CppBase::RemoveFile(int filei) { Index h; diff --git a/uppsrc/CppBase/CppBase.h b/uppsrc/CppBase/CppBase.h index 6f4404672..d49bdb7f6 100644 --- a/uppsrc/CppBase/CppBase.h +++ b/uppsrc/CppBase/CppBase.h @@ -5,8 +5,11 @@ namespace Upp { -// Functions in this header can be called without mutexes... - +struct CppBaseLock { // Use this in any function that is using CppBase + CppBaseLock(); + ~CppBaseLock(); +}; + bool IsCPPFile(const String& file); bool IsHFile(const String& path); @@ -147,6 +150,7 @@ struct CppBase : ArrayMap > { void Sweep(const Index& file, bool keep = true); void RemoveFiles(const Index& remove_file) { Sweep(remove_file, false); } void RemoveFile(int filei); + void Append(CppBase&& base); void Dump(Stream& s); }; diff --git a/uppsrc/CppBase/CppBase.upp b/uppsrc/CppBase/CppBase.upp index bd9476190..66db0c3b7 100644 --- a/uppsrc/CppBase/CppBase.upp +++ b/uppsrc/CppBase/CppBase.upp @@ -9,6 +9,7 @@ file keyword.i, ppconfig.cpp, macro.cpp, + util.cpp, ppfile.cpp, srcfiles.cpp, cpp.cpp, diff --git a/uppsrc/CppBase/Internal.h b/uppsrc/CppBase/Internal.h index 87638994e..159a26141 100644 --- a/uppsrc/CppBase/Internal.h +++ b/uppsrc/CppBase/Internal.h @@ -78,7 +78,9 @@ String GetIncludePath(); String GetSegmentFile(int segment_id); -const PPFile& GetPPFile(const char *path); +void MakePP(const Index& paths); // this is the only place to change PPFile info, cannot be run concurrently with anything else + +const PPFile& GetPPFile(const char *path); // only returns information created by MakePP String GetIncludePath(const String& s, const String& filedir); bool IncludesFile(const String& parent_path, const String& header_path); diff --git a/uppsrc/CppBase/Parser.cpp b/uppsrc/CppBase/Parser.cpp index df32da8bd..36c44de09 100644 --- a/uppsrc/CppBase/Parser.cpp +++ b/uppsrc/CppBase/Parser.cpp @@ -4,7 +4,7 @@ namespace Upp { #define LLOG(x) // DLOG(x) -#define LTIMING(x) DTIMING(x) +#define LTIMING(x) // DTIMING(x) void Parser::ThrowError(const String& e) { @@ -27,6 +27,7 @@ inline const char *bew(const char *s, const char *t) return t; } +// String == String comparison is likely faster than String == const char * comparison static String s_operator("operator"); static String s_virtual("virtual"); static String s_inline("inline"); diff --git a/uppsrc/CppBase/Pre.cpp b/uppsrc/CppBase/Pre.cpp index 0d44a1f8b..e78ada2d1 100644 --- a/uppsrc/CppBase/Pre.cpp +++ b/uppsrc/CppBase/Pre.cpp @@ -1,8 +1,7 @@ #include "CppBase.h" #include "Internal.h" -#define LTIMING(x) DTIMING(x) - +#define LTIMING(x) // DTIMING(x) namespace Upp { @@ -20,7 +19,6 @@ SrcFile::SrcFile() : SrcFile PreProcess(Stream& in, Parser& parser) // This is not really C preprocess, only removes (or processes) comment and directives { - DTIMING("PreProcess"); SrcFile res; bool include = true; int lineno = 0; @@ -67,12 +65,15 @@ SrcFile PreProcess(Stream& in, Parser& parser) // This is not really C preproces s[3] == 'i' && s[4] == 'n' && s[5] == 'e' && !iscid(s[6])) { s += 6; while(*s == ' ' || *s == '\t') s++; - String macro; + const char *b = s; while(iscid(*s)) - macro.Cat(*s++); + s++; + String macro(b, s); if(*s == '(') { + b = s; while(*s != ')' && *s) - macro.Cat(*s++); + s++; + macro.Cat(b, s); macro << ')'; } if(include) diff --git a/uppsrc/CppBase/Qualify.cpp b/uppsrc/CppBase/Qualify.cpp index 0271b8221..048ea42d2 100644 --- a/uppsrc/CppBase/Qualify.cpp +++ b/uppsrc/CppBase/Qualify.cpp @@ -4,7 +4,7 @@ namespace Upp { #define LLOG(x) // DLOG(x) -#define LTIMING(x) DTIMING(x) +#define LTIMING(x) // DTIMING(x) bool DoQualify(ScopeInfo& nf, const String& type, const String& usings, String& qt); diff --git a/uppsrc/CppBase/ScopeInfo.cpp b/uppsrc/CppBase/ScopeInfo.cpp index bde489d48..ab83d5a41 100644 --- a/uppsrc/CppBase/ScopeInfo.cpp +++ b/uppsrc/CppBase/ScopeInfo.cpp @@ -4,7 +4,7 @@ namespace Upp { #define LLOG(x) -#define LTIMING(x) DTIMING(x) +#define LTIMING(x) // DTIMING(x) ScopeInfo::ScopeInfo(const CppBase& base, int scopei) : scopei(scopei), base(base) diff --git a/uppsrc/CppBase/cpp.cpp b/uppsrc/CppBase/cpp.cpp index 400966b75..32c95572e 100644 --- a/uppsrc/CppBase/cpp.cpp +++ b/uppsrc/CppBase/cpp.cpp @@ -3,7 +3,7 @@ namespace Upp { -#define LTIMING(x) DTIMING(x) +#define LTIMING(x) // DTIMING(x) #define LLOG(x) // DLOG(x) void Cpp::ParamAdd(Vector& param, const char *s, const char *e) diff --git a/uppsrc/CppBase/cpplex.cpp b/uppsrc/CppBase/cpplex.cpp index 9da1333c5..7306767f8 100644 --- a/uppsrc/CppBase/cpplex.cpp +++ b/uppsrc/CppBase/cpplex.cpp @@ -160,13 +160,12 @@ void Lex::Next() if(c == '\0') return; switch(c) { case_id: { - String x; - x.Reserve(12); - x.Cat(c); + const char *b = ptr - 1; while(iscid(*ptr)) - x.Cat(*ptr++); + ptr++; + String x(b, ptr); int q = id.FindAdd(x); - if(q == tk_rval_ - 256) { // simple hack for transitionary macro + if(q == tk_rval_ - 256) { // simple hack for old rval macro AddCode('&'); AddCode('&'); } diff --git a/uppsrc/CppBase/ppfile.cpp b/uppsrc/CppBase/ppfile.cpp index ed18211e1..b9af82ed6 100644 --- a/uppsrc/CppBase/ppfile.cpp +++ b/uppsrc/CppBase/ppfile.cpp @@ -3,87 +3,31 @@ namespace Upp { -#define LTIMING(x) DTIMING(x) +#define LTIMING(x) // DTIMING(x) #define LLOG(x) // DLOG(x) -bool IsCPPFile(const String& path) -{ - return findarg(ToLower(GetFileExt(path)) , ".c", ".cpp", ".cc" , ".cxx", ".icpp") >= 0; -} +static std::atomic s_PPserial; +static VectorMap sAllMacros; // Only MakePP can write to this +static ArrayMap sPPfile; // Only MakePP can write to this -bool IsHFile(const String& path) -{ - return findarg(ToLower(GetFileExt(path)) , ".h", ".hpp", ".hxx" , ".hh") >= 0; -} +static VectorMap s_PathFileTime; +static StaticMutex s_PathFileTimeMutex; -void SetSpaces(String& l, int pos, int count) -{ - StringBuffer s(l); - memset(~s + pos, ' ', count); - l = s; -} +static VectorMap s_IncludePath; +static String s_Include_Path; +static StaticMutex s_IncludePathMutex; -const char *SkipString(const char *s) -{ - CParser p(s); - try { - p.ReadOneString(*s); - } - catch(CParser::Error) {} - s = p.GetPtr(); - while((byte)*(s - 1) <= ' ') - s--; - return s; -} +static StaticMutex s_FlatPPMutex; +static ArrayMap s_FlatPP; // ArrayMap to allow read access -void RemoveComments(String& l, bool& incomment) +int NextPPSerial() { - int q = -1; - int w = -1; - if(incomment) - q = w = 0; - else { - const char *s = l; - while(*s) { - if(*s == '\"') - s = SkipString(s); - else - if(s[0] == '/' && s[1] == '/') { - q = int(s - ~l); - SetSpaces(l, q, l.GetCount() - q); - return; - } - else - if(s[0] == '/' && s[1] == '*') { - q = int(s - ~l); - break; - } - else - s++; - } - if(q >= 0) - w = q + 2; - } - while(q >= 0) { - int eq = l.Find("*/", w); - if(eq < 0) { - incomment = true; - SetSpaces(l, q, l.GetCount() - q); - return; - } - SetSpaces(l, q, eq + 2 - q); - incomment = false; - q = l.Find("/*"); - w = q + 2; - } + return ++s_PPserial; } -static VectorMap sAllMacros; -static ArrayMap sPPfile; -static int sPPserial; - void SweepPPFiles(const Index& keep) { + CppBaseLock __; Index pp_segment_id; int unlinked_count = 0; for(int i = 0; i < sPPfile.GetCount(); i++) @@ -198,6 +142,10 @@ void PPFile::Parse(Stream& in) keywords.Clear(); int linei = 0; Md5Stream md5; + int current_serial = 0; + + VectorMap local_macro; // gather all macros first to reduce locking + while(!in.IsEof()) { String l = in.GetLine(); const char *ll = l; @@ -218,48 +166,75 @@ void PPFile::Parse(Stream& in) if(next_segment) { PPItem& m = item.Add(); m.type = PP_DEFINES; - m.segment_id = ++sPPserial; + m.segment_id = current_serial = NextPPSerial(); next_segment = false; - local_segments.Add(sPPserial); + local_segments.Add(current_serial); } CppMacro def; String id = def.Define(p.GetPtr()); if(id.GetCount()) { + PPMacro& l = local_macro.Add(id); + l.segment_id = current_serial; + l.line = linei; + l.macro = def; + /* PPMacro m; - m.segment_id = sPPserial; + m.segment_id = current_serial; m.line = linei; m.macro = def; ppmacro.Add(sAllMacros.Put(id, m)); + */ md5.Put("#", 1); md5.Put(id); md5.Put(0); - md5.Put(m.macro.md5, 16); + md5.Put(l.macro.md5, 16); } } else if(p.Id("undef")) { if(p.IsId()) { String id = p.ReadId(); - md5.Put("#", 1); - md5.Put(id); - md5.Put(1); + if(id.GetCount()) { + md5.Put("#", 1); + md5.Put(id); + md5.Put(1); + int q = local_macro.FindLast(id); // heuristic: only local undefs are allowed + while(q >= 0) { + PPMacro& um = local_macro[q]; + if(!um.macro.IsUndef()) { // found corresponding macro to undef + PPItem& m = item.Add(); + m.type = PP_DEFINES; + m.segment_id = current_serial = NextPPSerial(); + um.undef_segment_id = m.segment_id; + next_segment = true; + local_segments.Add(current_serial); + PPMacro& l = local_macro.Add(id); + l.segment_id = current_serial; + l.line = linei; + l.macro.SetUndef(); + } + q = local_macro.FindPrev(q); + } + } + /* int segmenti = -1; PPMacro *um = FindPPMacro(id, local_segments, segmenti); - if(um && segmenti) { // heuristic: only local undefs are allowed + if(um && segmenti) { PPItem& m = item.Add(); m.type = PP_DEFINES; - m.segment_id = ++sPPserial; + m.segment_id = current_serial = NextPPSerial(); um->undef_segment_id = m.segment_id; next_segment = true; - local_segments.Add(sPPserial); + local_segments.Add(current_serial); if(id.GetCount()) { PPMacro m; - m.segment_id = sPPserial; + m.segment_id = current_serial; m.line = linei; m.macro.SetUndef(); ppmacro.Add(sAllMacros.Put(id, m)); } } + */ } } else @@ -365,6 +340,10 @@ void PPFile::Parse(Stream& in) remove.Add(i++); } keywords.Remove(remove); + INTERLOCKED { // this is the only place that is allowed to write to sAllMacros + for(int i = 0; i < local_macro.GetCount(); i++) + ppmacro.Add(sAllMacros.Put(local_macro.GetKey(i), local_macro[i])); + } } void PPFile::Dump() const @@ -387,21 +366,50 @@ void PPFile::Dump() const DUMPC(includes); } -static VectorMap sIncludePath; -static ArrayMap sFlatPP; -static String sInclude_Path; - void PPSync(const String& include_path) { + CppBaseLock __; LLOG("* PPSync"); - sIncludePath.Clear(); - sFlatPP.Clear(); - sInclude_Path = include_path; + { + Mutex::Lock __(s_IncludePathMutex); + s_IncludePath.Clear(); + s_Include_Path = include_path; + } + { + Mutex::Lock __(s_FlatPPMutex); + s_FlatPP.Clear(); + } +} + +void InvalidateFileTimeCache() +{ + Mutex::Lock __(s_PathFileTimeMutex); + s_PathFileTime.Clear(); +} + +void InvalidateFileTimeCache(const String& path) +{ + LLOG("InvalidateFileTimeCache " << path); + Mutex::Lock __(s_PathFileTimeMutex); + s_PathFileTime.UnlinkKey(path); +} + +Time GetFileTimeCached(const String& p) +{ + LTIMING("GetFileTimeCached"); + Mutex::Lock __(s_PathFileTimeMutex); + int q = s_PathFileTime.Find(p); + if(q >= 0) + return s_PathFileTime[q]; + Time m = FileGetTime(p); + s_PathFileTime.Put(p, m); + return m; } String GetIncludePath() { - return sInclude_Path; + Mutex::Lock __(s_IncludePathMutex); + return s_Include_Path; } String GetIncludePath0(const char *s, const char *filedir) @@ -432,57 +440,47 @@ String GetIncludePath0(const char *s, const char *filedir) return Null; } -static VectorMap sPathFileTime; - -void InvalidateFileTimeCache() -{ - sPathFileTime.Clear(); -} - -void InvalidateFileTimeCache(const String& path) -{ - LLOG("InvalidateFileTimeCache " << path); - sPathFileTime.UnlinkKey(path); -} - -Time GetFileTimeCached(const String& p) -{ - LTIMING("GetFileTimeCached"); - int q = sPathFileTime.Find(p); - if(q >= 0) - return sPathFileTime[q]; - Time m = FileGetTime(p); - sPathFileTime.Put(p, m); - return m; -} - String GetIncludePath(const String& s, const String& filedir) { LTIMING("GetIncludePath"); + Mutex::Lock __(s_IncludePathMutex); String key; key << s << "#" << filedir; - int q = sIncludePath.Find(key); + int q = s_IncludePath.Find(key); if(q >= 0) - return sIncludePath[q]; + return s_IncludePath[q]; LTIMING("GetIncludePath 2"); String p = GetIncludePath0(s, filedir); - sIncludePath.Add(key, p); + s_IncludePath.Add(key, p); LLOG("GetIncludePath " << s << " " << filedir << ": " << p); return p; } +void MakePP(const Index& paths) +{ + Vector todo; + Vector pp; + for(int i = 0; i < paths.GetCount(); i++) { + String path = paths[i]; + PPFile& f = sPPfile.GetPut(path); + Time tm = GetFileTimeCached(path); + if(f.filetime != tm) { + f.filetime = tm; + pp.Add(&f); + todo.Add(path); + } + } + CoFor(todo.GetCount(), [&](int i) { + FileIn in(todo[i]); + pp[i]->Parse(in); + }); +} + const PPFile& GetPPFile(const char *path) { LTIMING("GetPPFile"); - Time tm = GetFileTimeCached(path); - PPFile& f = sPPfile.GetPut(path); - LLOG("GetPPFile " << path << ", " << f.filetime << ", " << tm); - if(f.filetime != tm) { - f.filetime = tm; - FileIn in(path); - f.Parse(in); - } - return f; + static PPFile zero; + return sPPfile.Get(path, zero); } bool IsSameFile(const String& f1, const String& f2) @@ -494,12 +492,13 @@ const FlatPP& GetFlatPPFile(const char *path, Index& visited) { LTIMING("GetFlatPPFile"); LLOG("GetFlatPPFile " << path); - int q = sFlatPP.Find(path); + Mutex::Lock __(s_FlatPPMutex); + int q = s_FlatPP.Find(path); if(q >= 0) { LLOG("From cache"); - return sFlatPP[q]; + return s_FlatPP[q]; } - FlatPP& fp = sFlatPP.Add(path); + FlatPP& fp = s_FlatPP.Add(path); const PPFile& pp = GetPPFile(path); int n = visited.GetCount(); visited.FindAdd(path); @@ -622,21 +621,26 @@ const Index& GetNamespaceEndMacros() void SetPPDefs(const String& defs) { + CppBaseLock __; sDefs = defs; LoadPPConfig(); } void CleanPP() { + CppBaseLock __; sAllMacros.Clear(); sPPfile.Clear(); - sPPserial = 0; + s_PPserial = 0; LoadPPConfig(); } void SerializePPFiles(Stream& s) { + CppBaseLock __; + int sPPserial = s_PPserial; s % sAllMacros % sPPfile % sPPserial; + s_PPserial = sPPserial; if(s.IsLoading()) LoadPPConfig(); diff --git a/uppsrc/CppBase/srcfiles.cpp b/uppsrc/CppBase/srcfiles.cpp index 0a4144546..5309d1c28 100644 --- a/uppsrc/CppBase/srcfiles.cpp +++ b/uppsrc/CppBase/srcfiles.cpp @@ -3,7 +3,7 @@ namespace Upp { -#define LTIMING(x) DTIMING(x) +#define LTIMING(x) // DTIMING(x) static VectorMap sSrcFile; static Index sIncludes; @@ -25,6 +25,7 @@ String NormalizeSourcePath(const String& path) void ClearSources() { + CppBaseLock __; sSrcFile.Clear(); sIncludes.Clear(); } @@ -41,6 +42,7 @@ const VectorMap& GetAllSourceMasters() void GatherSources(const String& master_path, const String& path_, Vector& parents) { + CppBaseLock __; String path = NormalizeSourcePath(path_); if(sSrcFile.Find(path) >= 0) return; @@ -50,11 +52,15 @@ void GatherSources(const String& master_path, const String& path_, Vector& sSrcFile.Add(path, master_path); parents.Add(ii); const PPFile& f = GetPPFile(path); + Index todo; for(int i = 0; i < f.includes.GetCount(); i++) { String p = GetIncludePath(f.includes[i], GetFileFolder(path)); if(p.GetCount()) - GatherSources(master_path, p, parents); + todo.FindAdd(p); } + MakePP(todo); // parse PP files in parallel to accelerate things... + for(String p : todo) + GatherSources(master_path, p, parents); parents.Drop(); } diff --git a/uppsrc/CppBase/util.cpp b/uppsrc/CppBase/util.cpp new file mode 100644 index 000000000..3d9d01cde --- /dev/null +++ b/uppsrc/CppBase/util.cpp @@ -0,0 +1,94 @@ +#include "CppBase.h" +#include "Internal.h" + +namespace Upp { + +static StaticMutex sGLock; +static thread_local int sGLockLevel = 0; + +CppBaseLock::CppBaseLock() +{ + if(sGLockLevel++ == 0) + sGLock.Enter(); +} + +CppBaseLock::~CppBaseLock() +{ + ASSERT(sGLockLevel > 0); + if(--sGLockLevel == 0) + sGLock.Leave(); +} + +bool IsCPPFile(const String& path) +{ + return findarg(ToLower(GetFileExt(path)) , ".c", ".cpp", ".cc" , ".cxx", ".icpp") >= 0; +} + +bool IsHFile(const String& path) +{ + return findarg(ToLower(GetFileExt(path)) , ".h", ".hpp", ".hxx" , ".hh") >= 0; +} + +void SetSpaces(String& l, int pos, int count) +{ + StringBuffer s(l); + memset(~s + pos, ' ', count); + l = s; +} + +const char *SkipString(const char *s) +{ + CParser p(s); + try { + p.ReadOneString(*s); + } + catch(CParser::Error) {} + s = p.GetPtr(); + while((byte)*(s - 1) <= ' ') + s--; + return s; +} + +void RemoveComments(String& l, bool& incomment) +{ + int q = -1; + int w = -1; + if(incomment) + q = w = 0; + else { + const char *s = l; + while(*s) { + if(*s == '\"') + s = SkipString(s); + else + if(s[0] == '/' && s[1] == '/') { + q = int(s - ~l); + SetSpaces(l, q, l.GetCount() - q); + return; + } + else + if(s[0] == '/' && s[1] == '*') { + q = int(s - ~l); + break; + } + else + s++; + } + if(q >= 0) + w = q + 2; + } + while(q >= 0) { + int eq = l.Find("*/", w); + if(eq < 0) { + incomment = true; + SetSpaces(l, q, l.GetCount() - q); + return; + } + SetSpaces(l, q, eq + 2 - q); + incomment = false; + q = l.Find("/*"); + w = q + 2; + } +} + +}; \ No newline at end of file diff --git a/uppsrc/CtrlLib/Progress.cpp b/uppsrc/CtrlLib/Progress.cpp index 658812740..ec1ab59c4 100644 --- a/uppsrc/CtrlLib/Progress.cpp +++ b/uppsrc/CtrlLib/Progress.cpp @@ -222,6 +222,8 @@ void Progress::SetText(const String& s) void Progress::Setxt() { + if(!IsMainThread()) + return; info = Format(text, pos); Process(); } diff --git a/uppsrc/ide/About.cpp b/uppsrc/ide/About.cpp index 4e53ddf82..9a92d4dea 100644 --- a/uppsrc/ide/About.cpp +++ b/uppsrc/ide/About.cpp @@ -65,6 +65,7 @@ Size SplashCtrl::MakeLogo(Ctrl& parent, Array& ctrl) Label& v1 = ctrl.Create