Подтвердить что ты не робот

Как работает extern в С#?

Всякий раз, когда я смотрю достаточно глубоко в отражатель, я сталкиваюсь с методами extern без источника. Я прочитал документацию msdn на http://msdn.microsoft.com/en-us/library/e59b22c5(v=vs.80).aspx. Что я получил от этой статьи, так это то, что методы с модификатором extern должны быть введены. Я интерпретировал это как означающее, что это работает как абстрактный шаблон factory. Я также заметил, что я никогда не видел нестатический метод extern. Является ли статическое объявление требованием (я мог видеть, как это имеет смысл)? Я все еще догадываюсь, и я не уверен, как это работает. Мне кажется, что компилятор должен распознавать определенные атрибуты, которые смягчают обработку, но я не знаю, какие атрибуты отличаются от тех, с которыми я столкнулся, например, MethodImplAttribute и DllImportAttribute из примера MSDN. Как кто-то использует атрибут extern? Он сказал, что во многих случаях это может повысить производительность. Кроме того, как я мог бы искать источник методов extern, таких как Object.InternalGetEquals()?

4b9b3361

Ответ 1

Рассмотрим раздел чтения 10.6.7 спецификации С#, который отвечает на многие ваши вопросы. Я воспроизведу часть его здесь для вашего удобства:


Когда объявление метода включает extern, этот способ быть внешним методом. внешний методы реализуются извне, обычно используя язык, отличный от С#. Потому что внешний метод в декларации нет фактических реализации, метод-тело внешний метод просто состоит из точка с запятой. Внешний метод может не быть общим. Модификатор extern обычно используется в сочетании с Атрибут DllImport, позволяя внешним методам реализованы с помощью DLL (Dynamic Link Библиотеки). Условия выполнения могут поддерживать другие механизмы, посредством которых реализации внешних методов могут быть предоставлены. Когда внешний метод включает атрибут DllImport, объявление метода должно также включить статический модификатор.


Как кто-то использует атрибут extern?

  • Напишите свой код на неуправляемом языке по вашему выбору.
  • Скомпилируйте его в DLL, экспортируя точку входа вашего кода.
  • Сделайте библиотеку interop, которая определяет метод как метод extern в данной DLL.
  • Вызовите его из С#.
  • Profit!

Как я буду искать источник внешних методов, таких как Object.InternalGetEquals()?

Перейдите к https://github.com/dotnet/coreclr/tree/master/src/vm

Ответ 2

Методы, помеченные extern с [DllImport] Обычно атрибуты называются библиотеками C. Эта функция полезна для вызова WinAPI или устаревшего кода.

Это пример из MSDN:

using System;
using System.Runtime.InteropServices;
class MainClass 
{
   [DllImport("User32.dll")]
   public static extern int MessageBox(int h, string m, string c, int type);

   static int Main() 
   {
      string myString; 
      Console.Write("Enter your message: ");
      myString = Console.ReadLine();
      return MessageBox(0, myString, "My Message Box", 0);
   }
}

Он вызывает MessageBox, который определен внутри библиотеки Windows user32.dll. Runtime делает всю тяжелую работу для вас здесь, хотя иногда вам нужно вручную управлять памятью. Если вы ошиблись в сигнатуре, ваша программа может выйти из строя при вызове, вы можете ввести утечку, иначе метод может вернуть что-то совершенно другое, поэтому будьте осторожны! Я нахожу pinvoke.net отличный инструмент для исправления подписей для разных API.

Некоторые методы extern внутри .NET Framework, у которых нет атрибута [DllImport], но украшены [MethodImpl (MethodImplOptions.InternalCall)], как правило, те, что реализованы в самой CLR, которая также написана на C. Некоторые из таких методов просто не могут быть реализованы на С#, поскольку они сами управляют самой средой выполнения, а некоторые реализованы на C, потому что их производительность критическая, а C - быстрее.

Это то, что MSDN говорит о них:

Задает внутренний вызов. Внутренний вызов - это вызов метода, который реализован в самой среде выполнения обычного языка.

Что касается фактического кода реализации, я сомневаюсь, что вы сможете получить его от Microsoft, но есть некоторые интересные альтернативные реализации CLR вокруг поэтому не забудьте проверить их.

Ответ 3

extern с вызовом платформы (pinvoke), чтобы облегчить управление сборками, вызывающими неуправляемый код. Ключевое слово extern информирует компилятор о необходимости создания правильного кода для обеспечения правильного маршалинга данных.

Ответ 4

Мы используем модификатор "extern" в объявлении метода. Он используется для указания того, что метод реализуется извне. Обычное использование модификатора "extern" имеет атрибут DllImport. С помощью этого атрибута управляются вызовы функций, отличных от С#. Если вы используете extern-модификатор, вы должны включить следующее пространство имен:

using System.Runtime.InteropServices;

Синтаксис выглядит как:

[DllImport("User32.dll")] public static extern int MessageBox(int h, string m, string c, int type);