开发者

What is unsafe in this code?

开发者 https://www.devze.com 2023-03-15 01:18 出处:网络
I am learning about managed and unmanaged code in CLR. So I wrote this example with C-style pointers in C#:

I am learning about managed and unmanaged code in CLR. So I wrote this example with C-style pointers in C#:

unsafe  static void Main(string[] args)
{
    int x;
    int* y;
    y = &x;
    *y = 50;
    Console.WriteLine(*y);
    Console.WriteLine(((int)y).ToString());
}

So I am wondering what really is unsafe in IL code that I got from the code above?

.assembly extern mscorlib
{}
.assembly UnsafePointers
{}
.module UnsafePointers.exe
.class private auto ansi beforefieldinit UnsafePointers.Program
extends [mscorlib]System.Object
{
    .method private hidebysig static void  Main(string[] args) cil managed
    {
        .entrypoint
        // Code size       34 (0x22)
        .locals init (int32 x,
        int32* y)
        IL_0001:  ldloca     x
        IL_0003:  conv.u
        IL_0004:  stloc      y
        IL_0005:  ldloc  y 
        IL_0006:  ldc.i4   50
        IL_0008:  stind.i4
        IL_0009:  ldloc      y
        IL_000a:  ldind.i4
        IL_000b:  call       void [mscorlib]System.Cons开发者_JAVA百科ole::WriteLine(int32)
        IL_0010:  nop
        IL_0011:  ldloca     y
        IL_0012:  conv.i4
        IL_0016:  call       instance string [mscorlib]System.Int32::ToString()
        IL_001b:  call       void [mscorlib]System.Console::WriteLine(string)
        IL_0021:  ret
    } 
}    

Does CLR manages this code? And what can go wrong with a code above?


What makes this code unsafe is the use of the 'ldind.i4' statement. This loads a signed 4-byte integer from a memory address. Any memory address can be given, allowing you to read from any memory address in the current process. This is considered unsafe and unverifiable. For instance, you could use this to look inside other appdomains, which is not allowed.


It's called unsafe, partly because it is not managed.

You can easily create c++ style memory leaks, there are no boundary checks, and other problems...

A nice article about unsafe code, also lists a few risks:

Using Unsafe Code in C#


Unsafe may not mean dangerous, but there is one thing that is important in unsafe code: it is unverifiable. This can mean several things, such as not checking the bounds of an array. In your simple example. there isn't that much dangerous or scary about it. It's pretty straight forward.

In can be unsafe because it also gets around most of the security mechanisms in the .NET Framework; which is why unsafe code requires Full Trust anyway.

Unsafe != Unmanaged. Unsafe just means it can manipulate pointers.


In general, the unsafe keyword allows you direct access to memory and therefore bypasses all verification and safety checks by the CLR.

Here's a good article on the use and impact of unsafe code: http://blogs.msdn.com/b/sebby1234/archive/2006/04/05/565090.aspx


By default, Microsoft’s C# and Visual Basic.NET compilers produce “safe” code. Safe code is code that is verifiably safe. However, using C#’s unsafe keyword or using other languages (such as C++ with Managed Extensions or IL Assembly language), you can produce code that cannot be verifiably safe. That is, the code might, in fact, be safe, but the verification is unable to prove it.

an administrator can elect to turn verification off (using the ".NET Management" Microsoft Management Console Snap-In). With verification off, the JIT compiler will compile unverifiable IL into native CPU instructions; however, the administrator is taking full responsibility for the code's behavior.

0

精彩评论

暂无评论...
验证码 换一张
取 消