[Mono-bugs] [Bug 61740][Wis] Changed - [PATCH] use test esi, 1, not mov eax,esi/and eax,1/test eax,eax

bugzilla-daemon@bugzilla.ximian.com bugzilla-daemon@bugzilla.ximian.com
Mon, 19 Jul 2004 18:38:09 -0400 (EDT)


Please do not reply to this email- if you want to comment on the bug, go to the
URL shown below and enter your comments there.

Changed by bmaurer@users.sf.net.

http://bugzilla.ximian.com/show_bug.cgi?id=61740

--- shadow/61740	2004-07-19 18:13:48.000000000 -0400
+++ shadow/61740.tmp.2220	2004-07-19 18:38:09.000000000 -0400
@@ -1,14 +1,14 @@
 Bug#: 61740
 Product: Mono: Runtime
 Version: unspecified
-OS: 
+OS: unknown
 OS Details: 
 Status: NEW   
 Resolution: 
-Severity: 
+Severity: Unknown
 Priority: Wishlist
 Component: misc
 AssignedTo: mono-bugs@ximian.com                            
 ReportedBy: bmaurer@users.sf.net               
 QAContact: mono-bugs@ximian.com
 TargetMilestone: ---
@@ -29,6 +29,85 @@
 Also, it does a similar optimization for membase loads.
 
 ------- Additional Comments From bmaurer@users.sf.net  2004-07-19 18:13 -------
 Created an attachment (id=8637)
 mini-test-esi-one.patch
 
+
+------- Additional Comments From bmaurer@users.sf.net  2004-07-19 18:38 -------
+interestingly, this increases code size. The reason is that test does
+not have an imm8 shortcut like and does. So you end up emitting longer
+code.
+
+However, GCC will always use test; also, the intel manual explicitly
+suggests the use of the idiom.
+
+GCC does some clever tricks to reduce the space overhead. Lets say you
+have:
+
+extern int foo;
+extern void do_foo ();
+
+static void x () {
+	if (foo & 1)
+		do_foo ();
+}
+
+what gcc will emit
+
+        test    BYTE PTR foo, 1
+        je      .L1
+        call    do_foo
+
+Since they use the byte version, an imm8 is emitted. if you do 
+
+extern int foo;
+extern void do_foo ();
+
+static void x () {
+	if (foo & (1 << 30))
+		do_foo ();
+}
+
+it will emit
+
+        test    BYTE PTR foo+3, 64
+        je      .L1
+        call    do_foo
+
+So, it basically finds the right part of the variable, and uses a byte
+pointer there.
+
+Another clever trick they do is to turn
+
+extern int foo;
+extern void do_foo ();
+
+static void x () {
+	if (foo & (1 << 31))
+		do_foo ();
+}
+
+into
+
+        cmp     DWORD PTR foo, 0
+        jns     .L1
+        call    do_foo
+
+[NB: jns here has no advantage over the byte trick, however, if you
+are dealing with a regvar rather than a memory address, it will help
+you out]
+
+Also, we could always use the imm16 version (as all registers have a
+16 bit alias). For e[abcd]x, we can use [abcd][lh] so that we get the
+imm8 benefits.
+
+Another transformation this patch should do is to turn
+
+if ((a & 1) == 1)
+
+to
+
+if ((a & 1) != 0)
+
+so that we can use the test trick. Of course, this only can be done if
+the constant is of the form 2^n.