Добрый день
Я пытаюсь использовать драйвер C SD / библиотеку файловой системы (Keil MDK) в проекте C ++ 11. Он был добавлен менеджером пакетов в Keil MDK 5.23. Я собираю с ARMCC 5.06u4
Я получаю предупреждение class "_ARM_MCI_STATUS"
не имеет подходящего конструктора копирования «, что странно, потому что заголовок, в котором он объявлен, имеет extern "C" {
,
По умолчанию пакет не имеет возможности установить его на C или C ++, но я вручную добавил файл в виде файла C. Все еще проблема.
Структура объявлена, в пределах extern "C" {
как:
typedef volatile struct _ARM_MCI_STATUS {
uint32_t command_active : 1; ///< Command active flag
uint32_t command_timeout : 1; ///< Command timeout flag (cleared on start of next command)
uint32_t command_error : 1; ///< Command error flag (cleared on start of next command)
uint32_t transfer_active : 1; ///< Transfer active flag
uint32_t transfer_timeout : 1; ///< Transfer timeout flag (cleared on start of next command)
uint32_t transfer_error : 1; ///< Transfer error flag (cleared on start of next command)
uint32_t sdio_interrupt : 1; ///< SD I/O Interrupt flag (cleared on start of monitoring)
uint32_t ccs : 1; ///< CCS flag (cleared on start of next command)
uint32_t reserved : 24;
} ARM_MCI_STATUS;
Проблема возникает, когда структура возвращается в:
static ARM_MCI_STATUS GetStatus (MCI_RESOURCES *mci) {
return mci->info->status;
}
куда status
объявлен как ARM_MCI_STATUS status;
, Я не понимаю, почему это должно быть проблемой.
Если я компилирую без —cpp, то он компилируется без проблем.
Какие-либо предложения?
Просто потому, что ваш struct
отмечен extern "C"
не означает, что он все равно не будет скомпилирован как код C ++.
Это означает, что return mci->info->status;
вызывает неявно сгенерированный конструктор копирования.
Так как _ARM_MCI_STATUS
отмечен volatile
, это члены, что означает конструктор копирования по умолчанию, который принимает T&
не может связываться с изменяемой ссылкой lvalue, которую она передала.
Это объясняется в объяснение:
В противном случае неявно объявленным конструктором копирования является T :: T (T).&). (Заметка
что из-за этих правил неявно объявленный конструктор копирования
не может связываться с изменчивым аргументом lvalue.)
А также в действующем стандарте (просто трудно найти правильное предложение, но оно там).
В C ++ конструктор копирования по умолчанию предназначен для константной ссылки.
Вы, однако, переходите в постоянную изменчивую ссылку; и по умолчанию для этого не создается конструктор копирования.
Возможно, вам будет лучше пометить каждый элемент вашей структуры как изменчивый, а не всю структуру.
Чтобы решить эту проблему в Keil µVision 5.23, я удалил глобальные флаги «—cpp». Затем я убедился, что все файлы C ++ находятся в своих собственных исходных группах в проекте. В опциях для этой группы на вкладке «C / C ++» в поле «Misc Controls» добавлен флаг «—cpp».
Опции можно получить, щелкнув правой кнопкой мыши на папке в представлении проекта.
На данный момент он компилируется без ошибок. Кажется, проблема в том, что µVision 5.23 скомпилирует все файлы, c или cpp, как C ++, если флаг —cpp установлен глобально. В отличие от Eclipse, кажется, нет способа установить разные флаги для файлов cpp и c.
Спасибо UKMonkey и Рику Эстли. Узнал кое-что о volatile и C ++.