Finishing an Introductory Look at CIL - The Inner Loop
(Page 6 of 7 )
Now we move on to the inner loop. The first thing we need to do is initialize everything. We'll need to assign a value of two to f, and we'll also need to assign the square root of i to limit. Let's tackle the former part first:
ldc.i4.2
stloc f
Now comes the harder part.
int limit = (int)Math.Sqrt(i);
There are two things that are important here. First, Sqrt takes a double. Second, Sqrt returns a double. Because of this, we need to do a little typecasting. We first need to push i onto the stack:
ldloc i
Now we need to convert it to a double and call Sqrt:
conv.r8
call float64 [mscorlib]System.Math::Sqrt(float64)
Finally, we need to convert it back to an integer and then store the result back in i:
conv.i4
stloc limit
Initialization is complete, and now it's time to move on to the condition part:
inner_condition:
ldloc f
ldloc limit
bgt inner_done
This should look very familiar, so we'll move on without further explanation. Inside the inner loop, we divide i by f and check for a remainder. As with addition, this is not very hard in CIL. We simply have to push the two numbers onto the stack and then perform the operation:
ldloc i
ldloc f
rem
The result (the remainder) is stored on the stack. If the number is not prime, then we'll eventually have a remainder of zero. So, we need to check for this, and if the remainder is indeed ever zero, then we need to jump out of the inner loop. Where do we jump to? Recall how we gave the outer loop's counter a label. If we jump here, then we totally bypass the rest of the inner loop. The value of i is then incremented, and we move into an iteration. This is what we want, and so we need to push zero onto the stack for comparison (remember that the remainder is already on the stack):
ldc.i4.0
Now we simply branch to the outer loop's counter if they are equal (“branch if equal” or “beq”):
beq outer_counter
If we haven't branched, we need to increment f and go back to the condition section:
ldc.i4.1
ldloc f
add
stloc f
br.s inner_condition
If the condition is false, then the loop is done, and the number is prime. We now need to print it out:
inner_done:
// the number is prime!
ldloc i
call void [mscorlib]System.Console::WriteLine(int32)
That's it! Assemble it and run it.
Next: Conclusion >>
More ASP.NET Articles
More By Peyton McCullough