Странное поведение с массивами char/uint8
Итак, я пытаюсь прочитать 8-байтовую строку символов с устройства I2C и распечатать ее на последовательной консоли. Этот необработанный массив из 8 символов не завершается, когда он поступает с устройства, поэтому я почти уверен, что мне придется завершить его вручную. К сожалению, когда я распечатываю полученную строку, последовательный монитор просто заполняется разрывами строк. Может ли кто-нибудь взглянуть на этот код и сказать мне, где я ошибся?
uint8_t* HT_Controller::readMultiple(uint8_t reg, uint8_t num)
{
Wire.beginTransmission(i2cAddr);
Wire.write(reg);
Wire.endTransmission();
Wire.requestFrom(i2cAddr, num);
uint8_t* data = new uint8_t[num];
for(int i = 0; i < num; i++)
{
data[i] = Wire.read();
}
return data;
}
char* HT_Controller::getManufacturer()
{
uint8_t* data = readMultiple(REGISTER_MFR, NUM_MFR_BYTES); //Читаем байты из контроллера
char* dataTerminated = new char[NUM_MFR_BYTES + 1]; //Наш новый массив, в конце которого будет нулевой символ
memcpy(data, dataTerminated, NUM_MFR_BYTES); //Копируем байты в новый массив
delete(data); //Мы закончили с исходным массивом, удаляем его из кучи
dataTerminated[NUM_MFR_BYTES] = 0; //Добавьте этот нулевой символ. Примечание: нам не нужно добавлять «+1» к индексу, поскольку массивы начинаются с 0, а не с 1.
return dataTerminated;
}
А вот как это используется в основном скетче:
void loop()
{
char* data = mc1->getManufacturer();
Serial.println(data);
delete(data);
delay(500);
}
1 ответ
Лучший ответ:
▲ 1
Ваш memcpy перевернут.
SYNOPSIS
#include <string.h>
void *memcpy(void *dest, const void *src, size_t n);
Итак, строка:
memcpy(data, dataTerminated, NUM_MFR_BYTES); //Копируем байты в новый массив
должно быть:
memcpy(dataTerminated, data, NUM_MFR_BYTES); //Копируем байты в новый массив
,
@Majenko
Смотрите также:
- Как отправить строку на мастер с помощью i2c
- Создание форматированной строки (включая числа с плавающей запятой) в Arduino-совместимом C++
- Arduino Преобразование std:string в String
- Использование StringStream в скетче Arduino
- Чтение строки, разделенной запятыми
- Какова цель F() и FPSTR() в ESP8266WebServer -> FSBrowser?
- Отправка строки из RPi в Arduino - Рабочий код
- Утечка памяти, вызванная конкатенацией строк
Подсказка №1: проверьте порядок параметров memcpy(), http://www.cplusplus.com/reference/cstring/memcpy/. И попробуйте написать код без использования кучи (создать/удалить)., @Mikael Patel
@MikaelPatel, как мне избежать использования кучи, учитывая, что это для библиотеки?, @You'reAGitForNotUsingGit
Совет №2: используйте стек и передавайте возвращаемые значения по ссылке. например, «char dataTerminate[NUM_MFR_BYTES + 1]; readMultiple(REGISTER_MFR, NUM_MFR_BYTES, dataTerminate);», @Mikael Patel
@MikaelPatel подожди, но разве возврат указателя на локальный массив не является нет-нет?, @You'reAGitForNotUsingGit
О, кажется, я понимаю, что ты имеешь в виду сейчас, @You'reAGitForNotUsingGit
@MikaelPatel хм, так что это все хорошо для
readMultiple()
, но чтобы применить это кgetManufacturer()
, пользователю нужно знать, что массив, который он передает для вывода, должен иметь длину 9 символов. ..., @You'reAGitForNotUsingGit