|
|
  |
void const *argument, Что это? |
|
|
|
Jan 6 2014, 20:18
|

Профессионал
    
Группа: Свой
Сообщений: 1 080
Регистрация: 16-11-04
Из: СПб
Пользователь №: 1 143

|
если оно будет на стеке, то по моменту запуска самой задачи естветсвено всё уплывет.
то есть так нельзя Suart_init mb_cfg = { 0, 9600 }; task_start( mb_task, ..., (void*)mb_cfg );
а так можно const Suart_init mb_cfg = { 0, 9600 }; task_start( mb_task, ..., (void*)mb_cfg );
или так static Suart_init mb_cfg = { 0, 9600 }; task_start( mb_task, ..., (void*)mb_cfg );
--------------------
Марс - единственная планета, полностью населенная роботами (около 7 штук).
|
|
|
|
|
Jan 6 2014, 20:35
|

Универсальный солдатик
     
Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362

|
Цитата(megajohn @ Jan 6 2014, 22:57)  то есть как реально в RTX синтаксис вызова не в курсе, но суть передал - вызов задач с конкретными параметрами. Спасибо! Понял. Проверил в действии. Работает. Нужно поправить - брать адрес структуры. Код task_start( mb_task, ..., (void*)&mb_cfg );
|
|
|
|
|
Jan 6 2014, 23:38
|
.
     
Группа: Участник
Сообщений: 4 005
Регистрация: 3-05-06
Из: Россия
Пользователь №: 16 753

|
Вообще-то компилятор должен "съедать" этот параметр при вызове функции и без явного преобразования. Как и для параметра "void *" компилятор должен принимать указатель на любой неконстантный объект из соответствующего адресного пространства. Если отказывается, то это наверное плохой компилятор. Без явного преобразования очевидно, что безопаснее. Цитата(ViKo @ Jan 7 2014, 02:35)  Нужно поправить - брать адрес структуры. Какая разница в данном случае, с амперсандом или без? В случае когда голый идентификатор структуры без указания поля. Однозначнее, конечно, было бы с амперсандом, но на данный момент в Си оба варианта вроде бы одинаковые. Цитата(megajohn @ Jan 7 2014, 02:18)  если оно будет на стеке, то по моменту запуска самой задачи естветсвено всё уплывет. Квалификатор const не запретит передачу локальной переменной. Не встать на грабли - забота программиста. const в параметре "проявит себя" только внутри тела функции, когда этот указатель без явного преобразования будет передан параметром или присвоен другому типизированному указателю на константу. Цитата(megajohn @ Jan 7 2014, 02:18)  то есть так нельзя Suart_init mb_cfg = { 0, 9600 }; task_start( mb_task, ..., (void*)mb_cfg );
а так можно const Suart_init mb_cfg = { 0, 9600 }; task_start( mb_task, ..., (void*)mb_cfg ); Второй вариант тоже будет на стеке. Просто менять его значения нельзя будет.
Сообщение отредактировал GetSmart - Jan 7 2014, 02:22
--------------------
Заблуждаться - Ваше законное право :-)
|
|
|
|
|
Jan 7 2014, 08:50
|

Универсальный солдатик
     
Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362

|
Цитата(GetSmart @ Jan 7 2014, 02:38)  Какая разница в данном случае, с амперсандом или без? В случае когда голый идентификатор структуры без указания поля. Однозначнее, конечно, было бы с амперсандом, но на данный момент в Си оба варианта вроде бы одинаковые. Возможно, в других языках варианты одинаковые. Но не в С. В C можно структуру передавать в функцию, именно, по значению, а не по ссылке. Т.е., имя структуры не есть ее адрес. В отличие от массива.
|
|
|
|
|
Jan 7 2014, 10:08
|
.
     
Группа: Участник
Сообщений: 4 005
Регистрация: 3-05-06
Из: Россия
Пользователь №: 16 753

|
Цитата(ViKo @ Jan 7 2014, 14:50)  Возможно, в других языках варианты одинаковые. Но не в С. Чем отличается результат двух вариантов выражений со структурами ниже? Код (void*)&mb_cfg и (void*)mb_cfg Если отличаются, то в каких компиляторах. Идентификатор/имя массива тоже не является адресом его первого элемента. Иначе выражение &mass было бы аналогом &(&mass[0]). Взятие адреса от адреса в Си допустимо?
Сообщение отредактировал GetSmart - Jan 7 2014, 10:18
--------------------
Заблуждаться - Ваше законное право :-)
|
|
|
|
|
Jan 7 2014, 10:18
|

Универсальный солдатик
     
Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362

|
Цитата(GetSmart @ Jan 7 2014, 13:08)  Чем отличается результат двух вариантов выражений со структурами ниже? Код (void*)&mb_cfg и (void*)mb_cfg Если отличаются, то в каких компиляторах. Тем, что второй вариант не компилируется. Keil V5.1.0 source\exsUSB.c(164): error: #171: invalid type conversion Led9_id = osThreadCreate(osThread(Led_thread), (void *)led9); А в каком компиляторе работают оба?
|
|
|
|
|
Jan 7 2014, 10:20
|

Профессионал
    
Группа: Свой
Сообщений: 1 080
Регистрация: 16-11-04
Из: СПб
Пользователь №: 1 143

|
Цитата(GetSmart @ Jan 7 2014, 03:38)  Квалификатор const не запретит передачу локальной переменной. Не встать на грабли - забота программиста. const в параметре "проявит себя" только внутри тела функции, когда этот указатель без явного преобразования будет передан параметром или присвоен другому типизированному указателю на константу. не знаю как в высших материях, но в дизамсе передается просто адрес. Задача компилятора - ругатся при попытке записи по const* Цитата(GetSmart @ Jan 7 2014, 03:38)  Второй вариант тоже будет на стеке. Просто менять его значения нельзя будет. если это AVR то будет во флеше, если ARM то как указано в линкере ROM_region. А в других архитектурах как решит компиляторы, но размещать const на стеке вызывающей задачи - сомнительно. Цитата(ViKo @ Jan 7 2014, 00:35)  Нужно поправить - брать адрес структуры. Код task_start( mb_task, ..., (void*)&mb_cfg ); да, мой косяк. Вместо компилятора под руками была текила, и это зло вчера меня победило
--------------------
Марс - единственная планета, полностью населенная роботами (около 7 штук).
|
|
|
|
|
Jan 7 2014, 10:38
|
.
     
Группа: Участник
Сообщений: 4 005
Регистрация: 3-05-06
Из: Россия
Пользователь №: 16 753

|
Цитата(ViKo @ Jan 7 2014, 16:18)  Led9_id = osThreadCreate(osThread(Led_thread), (void *)led9); А в каком компиляторе работают оба?  Предъявите объявление led9. Проверьте для корректности все предыдущие версии Кейла. Если раньше оба варианта допускались, то как разработчики это обосновали и обосновали ли? Цитата(megajohn @ Jan 7 2014, 16:20)  если это AVR то будет во флеше, То есть от компилятора не зависит? Цитата(megajohn @ Jan 7 2014, 16:20)  не знаю как в высших материях, но в дизамсе передается просто адрес. Задача компилятора - ругатся при попытке записи по const* Я имел ввиду "проявит себя" на этапе компиляции. По сути то же самое. Вне тела функции наличие квалификатора const никак не ограничивает передачу параметров по сравнению с вариантом без квалификатора const (в прототипе функции).
Сообщение отредактировал GetSmart - Jan 7 2014, 10:50
--------------------
Заблуждаться - Ваше законное право :-)
|
|
|
|
|
Jan 7 2014, 10:42
|

Универсальный солдатик
     
Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362

|
Цитата(GetSmart @ Jan 7 2014, 13:29)  Предъявите объявление led9. CODE typedef struct { uint16_t leds; uint32_t dels; } thread_init;
const thread_init led8 = {0x0100, 500}; const thread_init led9 = {0x0200, 498}; const thread_init led10 = {0x0400, 496}; const thread_init led11 = {0x0800, 494}; const thread_init led12 = {0x1000, 492}; const thread_init led13 = {0x2000, 490}; const thread_init led14 = {0x4000, 488}; const thread_init led15 = {0x8000, 486};
void Led_thread(void const *arg); // прототип
osThreadId Led8_id; osThreadId Led9_id; osThreadId Led10_id; osThreadId Led11_id; osThreadId Led12_id; osThreadId Led13_id; osThreadId Led14_id; osThreadId Led15_id;
osThreadDef(Led_thread, osPriorityNormal, 1, 0);
int32_t main(void) { ... Led8_id = osThreadCreate(osThread(Led_thread), (void *)&led8); Led9_id = osThreadCreate(osThread(Led_thread), (void *)&led9); Led10_id = osThreadCreate(osThread(Led_thread), (void *)&led10); Led11_id = osThreadCreate(osThread(Led_thread), (void *)&led11); Led12_id = osThreadCreate(osThread(Led_thread), (void *)&led12); Led13_id = osThreadCreate(osThread(Led_thread), (void *)&led13); Led14_id = osThreadCreate(osThread(Led_thread), (void *)&led14); Led15_id = osThreadCreate(osThread(Led_thread), (void *)&led15); ... }
void Led_thread(void const *arg) { while (true) { GPIOB->BSRR = ((thread_init *)arg)->leds; osDelay(((thread_init *)arg)->dels); GPIOB->BSRR = ((thread_init *)arg)->leds << 16; osDelay(((thread_init *)arg)->dels); } }
|
|
|
|
|
  |
2 чел. читают эту тему (гостей: 2, скрытых пользователей: 0)
Пользователей: 0
|
|
|