|
Как я получил Адъ, sizeof string |
|
|
|
May 12 2015, 08:05
|

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

|
Цитата(V_G @ May 12 2015, 10:50)  Поищите в вашей версии Си функцию типа strlen. Использовать функцию sizeof для строки некорректно, она для другого предназначена.
ЗЫ. Посмотрите в отладчике, ваша строка, размещенная в памяти, нулем завершается? Все функции вычисления длины строки ищут окончание в виде нулевого байта. Нулем завершается, конечно. Написал по-простому: char Buff[] = "Hello, ViKo!\r\n"; CDC_Transmit_FS((uint8_t *)Buff, sizeof Buff); Все передается, и нуль тоже. Hello, ViKo!<\r><\n><\0> Мне непонятно, sizeof указателя должен же быть равен 4 для Cortex. Почему один символ передается? Так нормально работает, спасибо! char *Buff = "Hello, ViKo!\r\n"; CDC_Transmit_FS((uint8_t *)Buff, strlen (Buff));
|
|
|
|
|
May 12 2015, 08:18
|

Местный
  
Группа: Участник
Сообщений: 329
Регистрация: 23-04-14
Пользователь №: 81 502

|
Цитата(ViKo @ May 12 2015, 08:42)  Что же, компилятор не знает длину строки, что хранит в своих таблицах? А в чем проблема-то ? Читайте Кернигана с Ритчи и голова болеть не будет. Там все написано. -- объявление указателя на инициализированный участок памяти char* Buf = "abc"; sizeof(Buf) - это размер указателя на строку, в вашем случае, похоже, 4 байта. sizeof(*Buf) - размер типа данных, на который этот указатель указывает, то есть char, в вашем сулчае 1 байт. -- объявление _массива_ char Arr1[] = "asdf"; sizeof(Arr1) == sizeof(char)*_5_; int Arr2[] = {1,2,3}; sizeof(Arr2) == sizeof(int)*3; Длинна строки не обязательно должна быть равна длинне массива. const char Str1 = "abcd\0asdf"; Длинна строки Str1 будет 4 символа.
|
|
|
|
|
May 12 2015, 17:12
|

Местный
  
Группа: Участник
Сообщений: 329
Регистрация: 23-04-14
Пользователь №: 81 502

|
Цитата(ViKo @ May 12 2015, 17:15)  Можно подставить макроопределение вместо строки. #define STR_HI_ALL "Hi, All!" char *Buff = STR_HI_ALL; CDC_Transmit_FS((uint8_t *)Buff, sizeof(STR_HI_ALL)); Результат не проверял. Дома не на чем. На кой? Чтоб запутать потенциального противника ? Было же уже решение для вашего (непонятно зачем) случая: const char szStr[] ="abcd"; Кстати, функция CDC_Transmit_FS() объявлена коряво. По-хорошему, ее надо сделать такой: void CDC_Transmit_FS(const void* apData, uint8_t aNumBytes); Тогда не надо будет кастить первый аргумено при ее вызове с любым типом данных
|
|
|
|
|
May 13 2015, 13:16
|
Частый гость
 
Группа: Свой
Сообщений: 113
Регистрация: 25-10-07
Из: Краснодар
Пользователь №: 31 725

|
Цитата А длину строки, на которую указывает указатель, только с помощью strlen вычислять? Если строка не меняется между вызовами, то через sizeof(Buff) - 1 Код const uint8_t Buff[] = "Hello, ViKo!\r\n"; CDC_Transmit_FS(Buff, sizeof(Buff) - 1); Цитата Это камень в бошки программистов STM32Cube Не вдаваясь в подробности реализации CDC_Transmit_FS внутри функции указатель типа uint8_t * проще инкрементировать или обращаться к произвольному элементу по индексу.
|
|
|
|
|
May 13 2015, 14:17
|

Гуру
     
Группа: Модераторы
Сообщений: 8 455
Регистрация: 15-05-06
Из: Рига, Латвия
Пользователь №: 17 095

|
Цитата(desh @ May 13 2015, 17:07)  Функция CDC_Transmit_FS передает данные Вот именно, что данные. Которые совсем не обязательно будут массивом байтов. Поэтому возлагать на пользователя необходимость захламлять исходник явными приведениями типа указателя на эти данные к указателю на массив байтов по меньшей мере непрофессионально. Кроме всего прочего параметр должен быть указателем именно на константные данные, потому что функция эти данные не меняет, значит а) может работать и с константными данными (из флеша) и б) константность помогает компилятору сгенерить более оптимальный код. Все это вопросы хорошего стиля и подобные ляпы в примерах от производителя чести этому производителю не делают. сравните: Код uint8_t CDC_Transmit_FS(uint8_t* Buf, uint16_t Len) { .... }
void test() { static char const Hello_string[] = "Слава мне, победителю драконов!";
CDC_Transmit_FS((uint8_t*)Hello_string, sizeof(Hello_string) - 1); } и Код uint8_t CDC_Transmit_FS(void const * psrc, uint16_t Len) { uint8_t const * Buf = (uint8_t const *)psrc; .... }
void test() { static char const Hello_string[] = "Слава мне, победителю драконов!";
CDC_Transmit_FS(Hello_string, sizeof(Hello_string) - 1); } одна строка в исходнике библиотечной функции разгружает от мусора исходник приложения и позволяет сосредоточится на решении задачи.
--------------------
На любой вопрос даю любой ответ"Write code that is guaranteed to work, not code that doesn’t seem to break" ( C++ FAQ)
|
|
|
|
|
May 13 2015, 14:47
|

неотягощённый злом
     
Группа: Свой
Сообщений: 2 746
Регистрация: 31-01-08
Из: Санкт-Петербург
Пользователь №: 34 643

|
Цитата(ViKo @ May 12 2015, 19:15)  Однако, sizeof вычисляется на этапе компиляции (обычно), а strlen нет. Зависит от компилятора. Например GCC благодаря Built-in Functions умеет считать длину константной строки на этапе компиляции даже при использовании strlen.
--------------------
“Будьте внимательны к своим мыслям - они начало поступков” (Лао-Цзы)
|
|
|
|
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|