Пустые структуры в C - PullRequest
       53

Пустые структуры в C

0 голосов
/ 28 декабря 2018

http://c0x.coding -guidelines.com / 6.7.2.1.html :

1401 Если список объявляемых структур не содержит именованных членов, поведение не определено.

Означает ли это, что следующее недопустимо?

struct C { };

Или что это значит?

Я использовал Convention=>C указатель Ada на пустойstruct (фактически пустая запись Ada), чтобы служить вместо void* в моих привязках библиотеки C (потому что в Ada нет void*).Интересно, неверно ли это.

Что я неправильно понимаю?


См. Также «Не передавать и не возвращать структуры без полей ненулевого размера в функции extern (C)».. Согласно C11 6.7.2.1p8 это неопределенное поведение. "в https://dlang.org/spec/struct.html

Ответы [ 2 ]

0 голосов
/ 04 января 2019

С точки зрения написания привязки Ada к библиотеке C, не имеет значения, какой тип доступа Ada Convention-C используется для void*.Вы никогда не будете ничего делать с объектами типа, кроме как передавать их импортированным функциям C.Я обычно использую

type Void_Ptr is access all Integer;
pragma Convention (C, Void_Ptr);
0 голосов
/ 28 декабря 2018

Очень мало в C нелегально, то есть вы не можете этого сделать.Скорее, многие вещи не определены стандартом C, а это означает, что, если вы их сделаете, стандарт C не говорит, что произойдет.Структуры без именованных элементов - это такая вещь.

C 2018 6.7.2.1 8 говорит, частично:

Если список struct-объявление-списка не содержит именованных элементов,либо напрямую, либо через анонимную структуру или анонимный союз, поведение не определено.

Если вам нужно что-то, что служит «неизвестным типом» и не хотите использовать void, тогда вы можетеобъявите структуру, тег которой известен, но содержимое которой отсутствует, например:

struct foo;

Затем вы можете использовать указатели на такие структуры (например, вы можете определить указатель struct foo *p;), но компиляторне будет знать размер или содержимое таких структур, поэтому он не может помочь вам распределить их, управлять массивами или использовать их иначе, чем путем передачи указателей вокруг и запроса внешних подпрограмм (которые действительно знают о содержимом).

Обычно в операциях между подпрограммами C в одном модуле и подпрограммами C в другом модуле:

  • В одном исходном модуле, который не зналДля содержимого структуры вы должны использовать указатель (struct foo *).
  • Другой модуль-источник (часто какая-то программная библиотека) будет знать о содержимом структуры.В своем собственном исходном коде он будет определять полную структуру с помощью struct foo { /* various things */ };, и он будет обслуживать эту структуру для первого модуля.
  • Между двумя такими модулями C правила стандарта C будутопределите поведение.

Поскольку вы взаимодействуете между C и Ada, правила для этих взаимодействий должны быть предоставлены вашими реализациями C и Ada.

...