[Mono-devel-list] Patch for Bug 45976

Marco Craveiro marco_craveiro at oceanus.plus.com
Mon Jan 19 17:08:23 EST 2004


hello Francois,

thanks for your time and for the favorable comments, its my first patch 
:-) i can't read Uma's patch (strange encoding) but i've got one
question regarding your mail:

> I attach the patch of Marco ( with a little modifcation in the new 
> method Interval::Intersect ) and the regression test.

what modification is it? can't see the difference in Intersects... 

at any rate, since System.Text.RegularExpressions seems to be in very
good hands i'll probably search for another bug to squash :-)

cheers,

marco

On Mon, 2004-01-19 at 18:27, Francois Beauchemin wrote:
> Hi !
> 
> Marco Cravairo has posted another patch for this bug.  ( See : 
> http://lists.ximian.com/archives/public/mono-list/2004-January/017642.html )
> 
> I've just reviewed his patch and it work well. A quick look to your 
> patch show you adressed the problem at a different angle. You modified 
> the interpreter and Marco has modified the CaracterClass class to adjust 
> a range to contain Uppercase and lower-case char when using ignore case.
> 
> I've done a little regression test ( attached ) and your patch does not 
> pass one test.
> 
> I attach the patch of Marco ( with a little modifcation in the new 
> method Interval::Intersect ) and the regression test.
> 
> In my opinion, your approach  is more optimized but at least one case is 
> not adressed
> 
> For example the regex [A-a] should match the string "[" since [ is 
> between uppercase and lowercase char in the asscii table ...
> 
> Francois Beauchemin
> 
> 
> ______________________________________________________________________
> Index: RegexBugs.cs
> ===================================================================
> RCS file: /mono/mcs/class/System/Test/System.Text.RegularExpressions/RegexBugs.cs,v
> retrieving revision 1.3
> diff -u -r1.3 RegexBugs.cs
> --- RegexBugs.cs	7 Jan 2004 18:24:11 -0000	1.3
> +++ RegexBugs.cs	19 Jan 2004 15:55:03 -0000
> @@ -70,5 +70,30 @@
>  			AssertEquals ("MEG #12", true, Regex.IsMatch(str, @"(something|dog|)*$"));
>  
>  		}
> +
> +                [Test]
> +                public void RangeIgnoreCase() // bug 45976
> +                {
> +                        string str = "AAABBBBAAA" ;
> +                        AssertEquals("RIC #01", true, Regex.IsMatch(str, @"[A-F]+", RegexOptions.IgnoreCase));
> +                        AssertEquals("RIC #02", true, Regex.IsMatch(str, @"[a-f]+", RegexOptions.IgnoreCase));
> +                        AssertEquals("RIC #03", true, Regex.IsMatch(str, @"[A-Fa-f]+", RegexOptions.IgnoreCase));
> +                        AssertEquals("RIC #04", true, Regex.IsMatch(str, @"[AB]+", RegexOptions.IgnoreCase));
> +                        AssertEquals("RIC #05", true, Regex.IsMatch(str, @"[A-B]+", RegexOptions.IgnoreCase));
> +
> +                        str = "AaaBBBaAa" ;
> +                        AssertEquals("RIC #06", true, Regex.IsMatch(str, @"[A-F]+", RegexOptions.IgnoreCase));
> +                        AssertEquals("RIC #07", true, Regex.IsMatch(str, @"[a-f]+", RegexOptions.IgnoreCase));
> +                        AssertEquals("RIC #08", true, Regex.IsMatch(str, @"[A-Fa-f]+", RegexOptions.IgnoreCase));
> +                        AssertEquals("RIC #09", true, Regex.IsMatch(str, @"[AB]+", RegexOptions.IgnoreCase));
> +                        AssertEquals("RIC #10", true, Regex.IsMatch(str, @"[A-B]+", RegexOptions.IgnoreCase));
> +
> +			str = "Aaa[";
> +			AssertEquals("RIC #11", true, Regex.IsMatch(str, @"[A-a]+", RegexOptions.IgnoreCase));
> +			
> +			str = "Ae";
> +			AssertEquals("RIC #12", false, Regex.IsMatch(str, @"[A-a]+", RegexOptions.IgnoreCase));
> +
> +                }
>  	}
>  }
> 
> ______________________________________________________________________
> ? regexIgnoreCase.patch
> ? regexUnified.patch
> ? regexUnified2.patch
> Index: interval.cs
> ===================================================================
> RCS file: /mono/mcs/class/System/System.Text.RegularExpressions/interval.cs,v
> retrieving revision 1.1
> diff -u -r1.1 interval.cs
> --- interval.cs	31 Jan 2002 08:00:16 -0000	1.1
> +++ interval.cs	19 Jan 2004 15:16:22 -0000
> @@ -95,6 +95,14 @@
>  			return low <= i && i <= high;
>  		}
>  
> +		public bool Intersects (Interval i) {
> + 			if (IsEmpty || i.IsEmpty)
> + 				return false;
> + 			
> + 			return ((Contains (i.low) && !Contains (i.high)) ||
> +				(Contains (i.high) && !Contains (i.low)));
> + 		}	
> +
>  		public void Merge (Interval i) {
>  			if (i.IsEmpty)
>  				return;
> Index: syntax.cs
> ===================================================================
> RCS file: /mono/mcs/class/System/System.Text.RegularExpressions/syntax.cs,v
> retrieving revision 1.1
> diff -u -r1.1 syntax.cs
> --- syntax.cs	31 Jan 2002 08:00:16 -0000	1.1
> +++ syntax.cs	19 Jan 2004 15:16:23 -0000
> @@ -779,11 +779,39 @@
>  		}
>  
>  		public void AddCharacter (char c) {
> -			intervals.Add (new Interval (c, c));
> +			// TODO: this is certainly not the most efficient way of doing things 
> + 			// TODO: but at least it produces correct results. 
> + 			AddRange (c, c);
>  		}
>  
>  		public void AddRange (char lo, char hi) {
> -			intervals.Add (new Interval (lo, hi));
> +			Interval new_interval = new Interval (lo, hi);
> + 
> + 			// ignore case is on. we must make sure our interval does not
> + 			// use upper case. if it does, we must normalize the upper case
> + 			// characters into lower case. 
> + 			if (ignore) {
> + 				if (upper_case_characters.Intersects (new_interval)) {
> + 					Interval partial_new_interval;
> + 
> + 					if (new_interval.low < upper_case_characters.low) {
> + 						partial_new_interval = new Interval (upper_case_characters.low + distance_between_upper_and_lower_case, 
> + 										     new_interval.high +  distance_between_upper_and_lower_case);
> + 						new_interval.high = upper_case_characters.low - 1;
> + 					}
> + 					else {
> + 						partial_new_interval = new Interval (new_interval.low + distance_between_upper_and_lower_case, 
> + 										     upper_case_characters.high + distance_between_upper_and_lower_case);
> + 						new_interval.low = upper_case_characters.high + 1;
> + 					}
> + 					intervals.Add (partial_new_interval);
> + 				}
> + 				else if (upper_case_characters.Contains (new_interval)) {
> + 					new_interval.high += distance_between_upper_and_lower_case;
> + 					new_interval.low += distance_between_upper_and_lower_case;
> + 				}
> + 			}
> + 			intervals.Add (new_interval);
>  		}
>  
>  		public override void Compile (ICompiler cmp, bool reverse) {
> @@ -871,6 +899,8 @@
>  				return 3;					// Range
>  		}
>  
> +		private static Interval upper_case_characters = new Interval ((char)65, (char)90);
> + 		private const int distance_between_upper_and_lower_case = 32;
>  		private bool negate, ignore;
>  		private bool[] pos_cats, neg_cats;
>  		private IntervalCollection intervals;




More information about the Mono-devel-list mailing list