Spec-Zone.ru › Ada 2012
Справочник по Ada 2012

B.3 Интерфейс с C и C++

Средства, относящиеся к интерфейсу с языком C и соответствующим подмножеством языка C++, — это пакет Interfaces.C и его дочерние пакеты, а также поддержка указания аспекта Convention со значениями convention_идентификатор C, C_Pass_By_Copy и любые из конвенций C_Variadic_n, описанных ниже.
Пакет Interfaces.C содержит основные типы, константы и подпрограммы, которые позволяют программе Ada передавать скаляры и строки функциям C и C++. При упоминании в этом подпункте сущности языка C, это также относится к соответствующим сущностям языка C++.

Статическая семантика

Библиотечный пакет Interfaces.C имеет следующую декларацию:
-- Декларации, основанные на <limits.h> C
CHAR_BIT : constant := определяется реализацией; -- обычно 8
SCHAR_MIN : constant := определяется реализацией; -- обычно –128
SCHAR_MAX : constant := определяется реализацией; -- обычно 127
UCHAR_MAX : constant := определяется реализацией; -- обычно 255
-- Целые со знаком и без знака
type int is range определяется реализацией;
type short is range определяется реализацией;
type long is range определяется реализацией;
type signed_char is range SCHAR_MIN .. SCHAR_MAX;
for signed_char'Size use CHAR_BIT;
type unsigned is mod определяется реализацией;
type unsigned_short is mod определяется реализацией;
type unsigned_long is mod определяется реализацией;
type unsigned_char is mod (UCHAR_MAX+1);
for unsigned_char'Size use CHAR_BIT;
subtype plain_char is определяется реализацией;
type ptrdiff_t is range определяется реализацией;
type size_t is mod определяется реализацией;
-- Числа с плавающей точкой
type C_float is digits определяется реализацией;
type double is digits определяется реализацией;
type long_double is digits определяется реализацией;
-- Символы и строки
type char is <тип символа, определенный реализацией>;
nul : constant char := определяется реализацией;
function To_C (Item : in Character) return char;
function To_Ada (Item : in char) return Character;
type char_array is array (size_t range <>) of aliased char
with Pack;
for char_array'Component_Size use CHAR_BIT;
function Is_Nul_Terminated (Item : in char_array) return Boolean;
function To_C (Item : in String;
Append_Nul : in Boolean := True)
return char_array;
function To_Ada (Item : in char_array;
Trim_Nul : in Boolean := True)
return String;
procedure To_C (Item : in String;
Target : out char_array;
Count : out size_t;
Append_Nul : in Boolean := True);
procedure To_Ada (Item : in char_array;
Target : out String;
Count : out Natural;
Trim_Nul : in Boolean := True);
-- Широкие символы и широкие строки
type wchar_t is <тип символа, определенный реализацией>;
wide_nul : constant wchar_t := определяется реализацией;
function To_C (Item : in Wide_Character) return wchar_t;
function To_Ada (Item : in wchar_t ) return Wide_Character;
type wchar_array is array (size_t range <>) of aliased wchar_t
with Pack;
Этот абзац был удален.
function Is_Nul_Terminated (Item : in wchar_array) return Boolean;
function To_C (Item : in Wide_String;
Append_Nul : in Boolean := True)
return wchar_array;
function To_Ada (Item : in wchar_array;
Trim_Nul : in Boolean := True)
return Wide_String;
procedure To_C (Item : in Wide_String;
Target : out wchar_array;
Count : out size_t;
Append_Nul : in Boolean := True);
procedure To_Ada (Item : in wchar_array;
Target : out Wide_String;
Count : out Natural;
Trim_Nul : in Boolean := True);
-- Типы, совместимые с ISO/IEC 10646:2003, определенные в ISO/IEC TR 19769:2004.
type char16_t is <тип символа, определенный реализацией>;
char16_nul : constant char16_t := определяется реализацией;
function To_C (Item : in Wide_Character) return char16_t;
function To_Ada (Item : in char16_t) return Wide_Character;
type char16_array is array (size_t range <>) of aliased char16_t
with Pack;
Этот абзац был удален.
function Is_Nul_Terminated (Item : in char16_array) return Boolean;
function To_C (Item : in Wide_String;
Append_Nul : in Boolean := True)
return char16_array;
function To_Ada (Item : in char16_array;
Trim_Nul : in Boolean := True)
return Wide_String;
procedure To_C (Item : in Wide_String;
Target : out char16_array;
Count : out size_t;
Append_Nul : in Boolean := True);
procedure To_Ada (Item : in char16_array;
Target : out Wide_String;
Count : out Natural;
Trim_Nul : in Boolean := True);
type char32_t is <тип символа, определенный реализацией>;
char32_nul : constant char32_t := определяется реализацией;
function To_C (Item : in Wide_Wide_Character) return char32_t;
function To_Ada (Item : in char32_t) return Wide_Wide_Character;
type char32_array is array (size_t range <>) of aliased char32_t
with Pack;
Этот абзац был удален.
function Is_Nul_Terminated (Item : in char32_array) return Boolean;
function To_C (Item : in Wide_Wide_String;
Append_Nul : in Boolean := True)
return char32_array;
function To_Ada (Item : in char32_array;
Trim_Nul : in Boolean := True)
return Wide_Wide_String;
procedure To_C (Item : in Wide_Wide_String;
Target : out char32_array;
Count : out size_t;
Append_Nul : in Boolean := True);
procedure To_Ada (Item : in char32_array;
Target : out Wide_Wide_String;
Count : out Natural;
Trim_Nul : in Boolean := True);
Terminator_Error : exception;
end Interfaces.C;
Каждый из типов, объявленных в Interfaces.C, совместим с C.
Типы int, short, long, unsigned, ptrdiff_t, size_t, double, char, wchar_t, char16_t и char32_t соответствуют соответственно типам C с такими же именами. Типы signed_char, unsigned_short, unsigned_long, unsigned_char, C_float и long_double соответствуют соответственно типам C signed char, unsigned short, unsigned long, unsigned char, float и long double.
Тип подтипа plain_char — это либо signed_char, либо unsigned_char, в зависимости от реализации C.
function To_C (Item : in Character) return char;
function To_Ada (Item : in char ) return Character;
Функции To_C и To_Ada выполняют преобразование между типом Ada Character и типом C char.
function Is_Nul_Terminated (Item : in char_array) return Boolean;
Результат Is_Nul_Terminated — True, если Item содержит nul, и False в противном случае.
function To_C (Item : in String; Append_Nul : in Boolean := True)
return char_array;

function To_Ada (Item : in char_array; Trim_Nul : in Boolean := True)
return String;
Результат To_C — значение char_array длиной Item'Length (если Append_Nul ложно) или Item'Length+1 (если Append_Nul истинно). Нижний предел — 0. Для каждого компонента Item(I) соответствующий компонент результата — результат применения To_C к Item(I). Значение nul добавляется, если Append_Nul истинно. Если Append_Nul ложно и Item'Length равно 0, то To_C распространяет Constraint_Error.
Результат To_Ada — строка, длина которой равна Item'Length (если Trim_Nul ложно) или длине части Item до первого nul (если Trim_Nul истинно). Нижний предел результата — 1. Если Trim_Nul ложно, то для каждого компонента Item(I) соответствующий компонент результата — результат применения To_Ada к Item(I). Если Trim_Nul истинно, то для каждого компонента Item(I) до первого nul соответствующий компонент результата — результат применения To_Ada к Item(I). Функция распространяет Terminator_Error, если Trim_Nul истинно и Item не содержит nul.
процедура To_C (Item : вход String;
Target : выход char_array;
Count : выход size_t;
Append_Nul : вход Boolean := True);

процедура To_Ada (Item : вход char_array;
Target : выход String;
Count : выход Natural;
Trim_Nul : вход Boolean := True);
Для процедуры To_C каждый элемент Item преобразуется (с помощью функции To_C) в символ, который присваивается соответствующему элементу Target. Если Append_Nul истинно, nul затем присваивается следующему элементу Target. В любом случае, Count устанавливается в число элементов Target, которым присвоено значение. Если Target недостаточно длинна, распространяется Constraint_Error.
Для процедуры To_Ada каждый элемент Item (если Trim_Nul ложно) или каждый элемент Item до первого nul (если Trim_Nul истинно) преобразуется (с помощью функции To_Ada) в символ, который присваивается соответствующему элементу Target. Count устанавливается в число элементов Target, которым присвоено значение. Если Target недостаточно длинна, распространяется Constraint_Error. Если Trim_Nul истинно и Item не содержит nul, то распространяется Terminator_Error.
функция Is_Nul_Terminated (Item : вход wchar_array) возвращает Boolean;
Результат Is_Nul_Terminated — True, если Item содержит wide_nul, и False в противном случае.
функция To_C (Item : вход Wide_Character) возвращает wchar_t;
функция To_Ada (Item : вход wchar_t ) возвращает Wide_Character;
To_C и To_Ada предоставляют отображения между типами широких символов Ada и C.
функция To_C (Item : вход Wide_String;
Append_Nul : вход Boolean := True)
возвращает wchar_array;

функция To_Ada (Item : вход wchar_array;
Trim_Nul : вход Boolean := True)
возвращает Wide_String;

процедура To_C (Item : вход Wide_String;
Target : выход wchar_array;
Count : выход size_t;
Append_Nul : вход Boolean := True);

процедура To_Ada (Item : вход wchar_array;
Target : выход Wide_String;
Count : выход Natural;
Trim_Nul : вход Boolean := True);
Подпрограммы To_C и To_Ada, которые преобразуют между Wide_String и wchar_array, имеют аналогичное действие подпрограммам To_C и To_Ada, которые преобразуют между String и char_array, за исключением того, что используется wide_nul вместо nul.
функция Is_Nul_Terminated (Item : вход char16_array) возвращает Boolean;
Результат Is_Nul_Terminated — True, если Item содержит char16_nul, и False в противном случае.
функция To_C (Item : вход Wide_Character) возвращает char16_t;
функция To_Ada (Item : вход char16_t ) возвращает Wide_Character;
To_C и To_Ada предоставляют отображения между типами 16-битовых символов Ada и C.
функция To_C (Item : вход Wide_String;
Append_Nul : вход Boolean := True)
возвращает char16_array;

функция To_Ada (Item : вход char16_array;
Trim_Nul : вход Boolean := True)
возвращает Wide_String;

процедура To_C (Item : вход Wide_String;
Target : выход char16_array;
Count : выход size_t;
Append_Nul : вход Boolean := True);

процедура To_Ada (Item : вход char16_array;
Target : выход Wide_String;
Count : выход Natural;
Trim_Nul : вход Boolean := True);
Подпрограммы To_C и To_Ada, которые преобразуют между Wide_String и char16_array, имеют аналогичное действие подпрограммам To_C и To_Ada, которые преобразуют между String и char_array, за исключением того, что используется char16_nul вместо nul.
функция Is_Nul_Terminated (Item : вход char32_array) возвращает Boolean;
Результат Is_Nul_Terminated — True, если Item содержит char16_nul, и False в противном случае.
функция To_C (Item : вход Wide_Wide_Character) возвращает char32_t;
функция To_Ada (Item : вход char32_t ) возвращает Wide_Wide_Character;
To_C и To_Ada предоставляют отображения между типами 32-битовых символов Ada и C.
функция To_C (Item : вход Wide_Wide_String;
Append_Nul : вход Boolean := True)
возвращает char32_array;

функция To_Ada (Item : вход char32_array;
Trim_Nul : вход Boolean := True)
возвращает Wide_Wide_String;

процедура To_C (Item : вход Wide_Wide_String;
Target : выход char32_array;
Count : выход size_t;
Append_Nul : вход Boolean := True);

процедура To_Ada (Item : вход char32_array;
Target : выход Wide_Wide_String;
Count : выход Natural;
Trim_Nul : вход Boolean := True);
Подпрограммы To_C и To_Ada, которые преобразуют между Wide_Wide_String и char32_array, имеют аналогичное действие подпрограммам To_C и To_Ada, которые преобразуют между String и char_array, за исключением того, что используется char32_nul вместо nul.
Аспект Convention с конвенцией_идентификатор C_Pass_By_Copy должен быть указан только для типа.
Правила применимости в B.1 не применяются к конвенции C_Pass_By_Copy. Вместо этого тип T подходит для конвенции C_Pass_By_Copy, если T — тип объединения без проверки или если T — тип записи без дискриминантов и только с компонентами со статически ограниченными подтипами, и каждый компонент совместим с C.
Если тип совместим с C_Pass_By_Copy, то он также совместим с C.
Идентификаторы C_Variadic_0, C_Variadic_1, C_Variadic_2 и т. д. являются конвенциями_идентификаторами. Эти конвенции называются C_Variadic. Конвенция C_Variadic_n — это соглашение вызова для вариативной C-функции, принимающей n фиксированных параметров, а затем переменное количество дополнительных параметров. Конвенция C_Variadic_n должна быть указана только как аспект соглашения для подпрограммы или типа доступа к подпрограмме, имеющей как минимум n параметров. Тип совместим с конвенцией C_Variadic тогда и только тогда, когда тип совместим с C.

Требования к реализации

Реализация должна поддерживать указание аспекта Convention с C-конвенцией_идентификатор для типа, совместимого с C (см. B.1). Реализация должна поддерживать указание аспекта Convention с C_Pass_By_Copy-конвенцией_идентификатор для типа, совместимого с C_Pass_By_Copy.

Разрешения для реализации

Реализация может предоставлять дополнительные объявления в пакетах интерфейса C.
Реализация может не поддерживать указание аспекта Convention с конвенцией_идентификатор C в следующих случаях:
  • для подпрограммы, имеющей параметр с неограниченным подтипом массива, если для подпрограммы аспект Import не имеет значения True;
  • для функции с неограниченным подтипом массива результата;
  • для объекта, номинальный подтип которого является неограниченным подтипом массива.

Рекомендации по реализации

Константы nul, wide_nul, char16_nul и char32_nul должны иметь представление нуля.
Реализация должна поддерживать следующие соответствия интерфейсов между Ada и C.
  • Процедура Ada соответствует возвращающей void C-функции.
  • Функция Ada соответствует не возвращающей void C-функции.
  • Тип перечисления Ada соответствует типу перечисления C с соответствующими именами перечислений, имеющими те же внутренние коды, при условии, что внутренние коды находятся в диапазоне типа C int.
  • Параметр Ada вход скалярного типа передаётся как скалярный аргумент в C-функцию.
  • Параметр Ada вход типа доступа к объекту с указанным типом T передаётся как t* аргумент в C-функцию, где t — тип C, соответствующий типу Ada T.
  • Параметр Ada доступ T или параметр Ada выход или вход-выход элементарного типа T передаётся как t* аргумент в C-функцию, где t — тип C, соответствующий типу Ada T. В случае элементарного параметра выход или вход-выход используется указатель на временную копию для сохранения семантики передачи по значению.
  • Параметр Ada типа (записи) T с конвенцией C_Pass_By_Copy, режима вход, передаётся как t аргумент в C-функцию, где t — структура C, соответствующая типу Ada T.
  • Параметр Ada типа записи T любого режима, кроме параметра вход типа с конвенцией C_Pass_By_Copy, передаётся как t* аргумент в C-функцию, где t — структура C, соответствующая типу Ada T.
  • Параметр Ada массива типа с компонентами типа T любого режима передаётся как t* аргумент в C-функцию, где t — тип C, соответствующий типу Ada T.
  • Параметр Ada типа доступа к подпрограмме передается как указатель на функцию C, прототип которой соответствует спецификации указанной подпрограммы.
  • Параметр Ada частного типа передается как указано для полного представления типа.
  • Приведенные выше правила соответствия для параметров режима in также применяются к возвращаемому объекту функции.
Этот абзац был удален.
ПРИМЕЧАНИЯ
6 Значения типа char_array не неявно завершаются нулем. Если char_array должен передаваться в качестве параметра импортированной функции C, требующей завершения нулем, программист обязан обеспечить это действие.
7 Чтобы получить эффект C's sizeof(item_type), где Item_Type — соответствующий тип Ada, вычислите выражение: size_t(Item_Type'Size/CHAR_BIT).
Этот абзац был удален.
8 Функция C с переменным числом аргументов может соответствовать нескольким подпрограммам Ada, принимающим различное число и типы параметров.

Примеры

Пример использования пакета Interfaces.C:
--Вызов функции библиотеки C strcpy
with Interfaces.C;
procedure Test is
package C renames Interfaces.C;
use type C.char_array;
-- Вызов <string.h>strcpy:
-- Определение strcpy в C: char *strcpy(char *s1, const char *s2);
-- Эта функция копирует строку, на которую указывает s2 (включая завершающий нулевой символ)
-- в массив, на который указывает s1. Если копирование происходит между перекрывающимися объектами,
-- поведение не определено. Функция strcpy возвращает значение s1.
-- Примечание: так как значение возврата функции C не интересно, интерфейс Ada является процедурой
procedure Strcpy (Target : out C.char_array;
Source : in C.char_array)
with Import => True, Convention => C, External_Name => "strcpy";
Этот абзац был удален.
Chars1 : C.char_array(1..20);
Chars2 : C.char_array(1..20);
begin
Chars2(1..6) := "qwert" & C.nul;
Strcpy(Chars1, Chars2);
-- Теперь Chars1(1..6) = "qwert" & C.Nul
end Test;


Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API