none
Can Anonymous Method Execute Unsafe Code Outside of an Unsafe Context RRS feed

  • Question

  •   This code functions, however I think it may be unsafe because the method is able to use a pointer after the unsafe context, which surrounds the pointer, has exited.  Is this a bug in the .NET framework.

      class Program
      {
        static void Main(string[] args)
        {
    
          int someInt = 0;
    
          Action someAction = null;
    
          unsafe
          {
            int* ptrToInt = &someInt;
    
            someAction = SomeMethod(ptrToInt);
          }
          
          someAction();
          
          return;
        }
    
        unsafe static Action SomeMethod(int* param)
        {
          
          Action someAction = new Action(() =>
          {
            *param = 2;
            return;
          });
          
          return someAction;
        }
      }
    

     

     

     

    Friday, June 17, 2011 6:13 PM

Answers

  • In the Main method, we invoke someAction delegate outside unsafe context, it doesn't matter whether the someAction points to a safe or unsafe method, the method invoking itself is safe, furthermore, we can also call an unsafe method from a safe method, for example:

     

        class Program

        {

            static void Main(string[] args)

            {

     

                int someInt = 0;

     

                Action someAction = null;

     

                unsafe

                {

                    int* ptrToInt = &someInt;

     

                    someAction = SomeMethod(ptrToInt);

                }

     

                someAction();

     

                UnsafeMethod();

     

                Console.WriteLine(someInt);

     

                return;

            }

     

            unsafe static Action SomeMethod(int* param)

            {

     

                Action someAction = new Action(() =>

                {

                    *param = 2;

                    return;

                });

     

                return someAction;

            }

     

            unsafe static void UnsafeMethod()

            {

                int value = 100;

                int* ptr = &value;

                Console.WriteLine(ptr->ToString());

            }

     


    Eric Yang [MSFT]
    MSDN Community Support | Feedback to us
    Get or Request Code Sample from Microsoft
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

    • Marked as answer by eryang Monday, July 11, 2011 6:36 AM
    Tuesday, June 21, 2011 1:30 AM
  • CIL internally supports Pointer Type, as long as Value Type and Reference Type; C# only expose Value Type and Reference Type to end user to provide safe code context, however, C# also provide unsafe context to support Pointer Type. So, the Safe or Unsafe Context is a concept of compile time, in other words, CIL always support Unsafe Code, but, to use Unsafe Code in C#, we need the unsafe keyword.

     

    In your code snippet, the Action delegate is in a unsafe context, so, the code compiled successfully and works well.


    Eric Yang [MSFT]
    MSDN Community Support | Feedback to us
    Get or Request Code Sample from Microsoft
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

    • Marked as answer by eryang Monday, July 11, 2011 6:36 AM
    Tuesday, June 28, 2011 8:36 AM

All replies

  • In the Main method, we invoke someAction delegate outside unsafe context, it doesn't matter whether the someAction points to a safe or unsafe method, the method invoking itself is safe, furthermore, we can also call an unsafe method from a safe method, for example:

     

        class Program

        {

            static void Main(string[] args)

            {

     

                int someInt = 0;

     

                Action someAction = null;

     

                unsafe

                {

                    int* ptrToInt = &someInt;

     

                    someAction = SomeMethod(ptrToInt);

                }

     

                someAction();

     

                UnsafeMethod();

     

                Console.WriteLine(someInt);

     

                return;

            }

     

            unsafe static Action SomeMethod(int* param)

            {

     

                Action someAction = new Action(() =>

                {

                    *param = 2;

                    return;

                });

     

                return someAction;

            }

     

            unsafe static void UnsafeMethod()

            {

                int value = 100;

                int* ptr = &value;

                Console.WriteLine(ptr->ToString());

            }

     


    Eric Yang [MSFT]
    MSDN Community Support | Feedback to us
    Get or Request Code Sample from Microsoft
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

    • Marked as answer by eryang Monday, July 11, 2011 6:36 AM
    Tuesday, June 21, 2011 1:30 AM
  • So the issue that to me seems to be problematic is not the fact that the delegate is safe or unsafe.  The issue is that the anonymous method can hold a reference to a pointer that was declared in an unsafe context and then can use the pointer after the unsafe context is exited.  The question that comes up is one of whether or not the pointer is still safe for the anonymous method to use once the unsafe context is out of scope.

     

    Myron




        class Program

        {

            static void Main(string[] args)

            {

     

                int someInt = 0;

     

                Action someAction = null;

     

                unsafe

                {

                    int* ptrToInt = &someInt;

     

                    someAction = SomeMethod(ptrToInt);

                }

     

                someAction();

     

                return;

            }

     

            unsafe static Action SomeMethod(int* param)

            {

     

                Action someAction = new Action(() =>

                {

                    *param = 2;

                    return;

                });

     

                return someAction;

            }

        }

    • Edited by Myron Walker Monday, June 27, 2011 4:35 PM Added highlighted code.
    Monday, June 27, 2011 4:27 PM
  • CIL internally supports Pointer Type, as long as Value Type and Reference Type; C# only expose Value Type and Reference Type to end user to provide safe code context, however, C# also provide unsafe context to support Pointer Type. So, the Safe or Unsafe Context is a concept of compile time, in other words, CIL always support Unsafe Code, but, to use Unsafe Code in C#, we need the unsafe keyword.

     

    In your code snippet, the Action delegate is in a unsafe context, so, the code compiled successfully and works well.


    Eric Yang [MSFT]
    MSDN Community Support | Feedback to us
    Get or Request Code Sample from Microsoft
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

    • Marked as answer by eryang Monday, July 11, 2011 6:36 AM
    Tuesday, June 28, 2011 8:36 AM