Browse Source

* after changing a modeswitch, only change related module/localswitches that
depend on the modeswitch that was just changed (so that e.g. changing
the nested procvars setting has no effect on the state of $h+/$h-)
(mantis #21951)

git-svn-id: trunk@21247 -

Jonas Maebe 13 years ago
parent
commit
50d2fa7134
3 changed files with 82 additions and 45 deletions
  1. 1 0
      .gitattributes
  2. 70 45
      compiler/scanner.pas
  3. 11 0
      tests/webtbs/tw21951.pp

+ 1 - 0
.gitattributes

@@ -12581,6 +12581,7 @@ tests/webtbs/tw2185.pp svneol=native#text/plain
 tests/webtbs/tw2186.pp svneol=native#text/plain
 tests/webtbs/tw2186.pp svneol=native#text/plain
 tests/webtbs/tw2187.pp svneol=native#text/plain
 tests/webtbs/tw2187.pp svneol=native#text/plain
 tests/webtbs/tw21878.pp svneol=native#text/plain
 tests/webtbs/tw21878.pp svneol=native#text/plain
+tests/webtbs/tw21951.pp svneol=native#text/plain
 tests/webtbs/tw2196.pp svneol=native#text/plain
 tests/webtbs/tw2196.pp svneol=native#text/plain
 tests/webtbs/tw2197.pp svneol=native#text/plain
 tests/webtbs/tw2197.pp svneol=native#text/plain
 tests/webtbs/tw2198.pp svneol=native#text/plain
 tests/webtbs/tw2198.pp svneol=native#text/plain

+ 70 - 45
compiler/scanner.pas

@@ -314,54 +314,79 @@ implementation
       end;
       end;
 
 
 
 
-    Procedure HandleModeSwitches(changeInit: boolean);
+    Procedure HandleModeSwitches(switch: tmodeswitch; changeInit: boolean);
       begin
       begin
-        { turn ansi/unicodestrings on by default ? }
-        if ([m_default_ansistring,m_default_unicodestring]*current_settings.modeswitches)<>[] then
-         begin
-           include(current_settings.localswitches,cs_refcountedstrings);
-           if changeinit then
-            include(init_settings.localswitches,cs_refcountedstrings);
-         end
-        else
-         begin
-           exclude(current_settings.localswitches,cs_refcountedstrings);
-           if changeinit then
-            exclude(init_settings.localswitches,cs_refcountedstrings);
-         end;
+        { turn ansi/unicodestrings on by default ? (only change when this
+          particular setting is changed, so that a random modeswitch won't
+          change the state of $h+/$h-) }
+        if switch in [m_all,m_default_ansistring,m_default_unicodestring] then
+          begin
+            if ([m_default_ansistring,m_default_unicodestring]*current_settings.modeswitches)<>[] then
+              begin
+                { can't have both ansistring and unicodestring as default }
+                if switch=m_default_ansistring then
+                  begin
+                    exclude(current_settings.modeswitches,m_default_unicodestring);
+                    if changeinit then
+                      exclude(init_settings.modeswitches,m_default_unicodestring);
+                  end
+                else if switch=m_default_unicodestring then
+                  begin
+                    exclude(current_settings.modeswitches,m_default_ansistring);
+                    if changeinit then
+                      exclude(init_settings.modeswitches,m_default_ansistring);
+                  end;
+                { enable $h+ }
+                include(current_settings.localswitches,cs_refcountedstrings);
+                if changeinit then
+                  include(init_settings.localswitches,cs_refcountedstrings);
+              end
+            else
+              begin
+                exclude(current_settings.localswitches,cs_refcountedstrings);
+                if changeinit then
+                  exclude(init_settings.localswitches,cs_refcountedstrings);
+              end;
+          end;
 
 
         { turn inline on by default ? }
         { turn inline on by default ? }
-        if (m_default_inline in current_settings.modeswitches) then
-         begin
-           include(current_settings.localswitches,cs_do_inline);
-           if changeinit then
-            include(init_settings.localswitches,cs_do_inline);
-         end
-        else
-         begin
-           exclude(current_settings.localswitches,cs_do_inline);
-           if changeinit then
-            exclude(init_settings.localswitches,cs_do_inline);
-         end;
-
-        { turn system codepage by default }
-        if m_systemcodepage in current_settings.modeswitches then
+        if switch in [m_all,m_default_inline] then
           begin
           begin
-            current_settings.sourcecodepage:=DefaultSystemCodePage;
-            if not cpavailable(current_settings.sourcecodepage) then
-              current_settings.sourcecodepage:=default_settings.sourcecodepage;
-            include(current_settings.moduleswitches,cs_explicit_codepage);
-            if changeinit then
-            begin
-              init_settings.sourcecodepage:=current_settings.sourcecodepage;
-              include(init_settings.moduleswitches,cs_explicit_codepage);
-            end;
-          end
-        else
+            if (m_default_inline in current_settings.modeswitches) then
+             begin
+               include(current_settings.localswitches,cs_do_inline);
+               if changeinit then
+                 include(init_settings.localswitches,cs_do_inline);
+             end
+            else
+             begin
+               exclude(current_settings.localswitches,cs_do_inline);
+               if changeinit then
+                 exclude(init_settings.localswitches,cs_do_inline);
+             end;
+          end;
+
+        { turn on system codepage by default }
+        if switch in [m_all,m_systemcodepage] then
           begin
           begin
-            exclude(current_settings.moduleswitches,cs_explicit_codepage);
-            if changeinit then
-              exclude(init_settings.moduleswitches,cs_explicit_codepage);
+            if m_systemcodepage in current_settings.modeswitches then
+              begin
+                current_settings.sourcecodepage:=DefaultSystemCodePage;
+                if not cpavailable(current_settings.sourcecodepage) then
+                  current_settings.sourcecodepage:=default_settings.sourcecodepage;
+                include(current_settings.moduleswitches,cs_explicit_codepage);
+                if changeinit then
+                begin
+                  init_settings.sourcecodepage:=current_settings.sourcecodepage;
+                  include(init_settings.moduleswitches,cs_explicit_codepage);
+                end;
+              end
+            else
+              begin
+                exclude(current_settings.moduleswitches,cs_explicit_codepage);
+                if changeinit then
+                  exclude(init_settings.moduleswitches,cs_explicit_codepage);
+              end;
           end;
           end;
       end;
       end;
 
 
@@ -422,7 +447,7 @@ implementation
            { resolve all postponed switch changes }
            { resolve all postponed switch changes }
            flushpendingswitchesstate;
            flushpendingswitchesstate;
 
 
-           HandleModeSwitches(changeinit);
+           HandleModeSwitches(m_all,changeinit);
 
 
            { turn on bitpacking for mode macpas and iso pascal }
            { turn on bitpacking for mode macpas and iso pascal }
            if ([m_mac,m_iso] * current_settings.modeswitches <> []) then
            if ([m_mac,m_iso] * current_settings.modeswitches <> []) then
@@ -579,7 +604,7 @@ implementation
                 end;
                 end;
 
 
               { set other switches depending on changed mode switch }
               { set other switches depending on changed mode switch }
-              HandleModeSwitches(changeinit);
+              HandleModeSwitches(i,changeinit);
 
 
               if changeInit then
               if changeInit then
                 init_settings.modeswitches:=current_settings.modeswitches;
                 init_settings.modeswitches:=current_settings.modeswitches;

+ 11 - 0
tests/webtbs/tw21951.pp

@@ -0,0 +1,11 @@
+{ %opt=-Mobjfpc -Sh }
+
+{$modeswitch exceptions}
+
+var
+  S: string;
+begin
+  SetLength(S, 1000);
+  if (length(s)<>1000) then
+    halt(1);
+end.