Tarbal 4 19 июня, 2016 Опубликовано 19 июня, 2016 · Жалоба Вроде нашел в чем дело. Я поначалу не знал, что хардвер чип селект не доделан и его нужно только вручную ставить. Ну и выбрал хардвер, где-то нашел, что для его снятия надо вызывать DISABLE_SPI(). Вроде обмен происходит, а поскольку проблема не возникла сразу, а SPI это мизерная часть моего проекта, то я не стал вникать в детали тогда. Что происходит. При каждой транзакции разрешается интерфейс и одновременно сигнал клока идет в единицу (клок инвертирован), чип селект в ноль. Если на клоке есть емкость, то он немного запаздывает и видимо воспринимается как первый фронт клока. Будет время переделаю на софтвер чипселект и расскажу. И де вы такое прочитали? :rolleyes: На ноль омов резисторов не бывает. :laughing: Бывают. С первого же сообщения (slave устройство...) и до последнего от топикстартера. Поскольку есть устройство, то гарантии, что оно выдает мощную единицу всегда - нет. Топикстартер мог даже и не разглядеть кратковременного провала в цепи, в зависимости от качества осциллографа и квалификации "наблюдателя". Ну осциллографом я пользоваться умею и никакого другого значения кроме единицы там не видел. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ViKo 1 19 июня, 2016 Опубликовано 19 июня, 2016 · Жалоба Бывают. Пе-ре-мыч-ки. Ну осциллографом я пользоваться умею и никакого другого значения кроме единицы там не видел. Назовите модель осциллографа, полосу частот, частоту дискретизации. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
adnega 11 19 июня, 2016 Опубликовано 19 июня, 2016 · Жалоба У меня есть STM32F429I-Disco. Если выложите код, похожий на нерабочий, могу посмотреть. Но с нуля писать лень. Вдруг не не заработает. :rolleyes: Короче, пытаюсь воспроизвести ошибку - не получается. Перепробовал SPI1, SPI4, SPI5. Точные номер SPI и номера пинов не помню. Хотел же тогда на электроникс запостить, но поленился описывать глюк. Итого: ошибку воспроизвести не могу; если кто сообщит номер SPI и номера пинов (и каналов DMA опционально), то могу попробовать на макете. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Tarbal 4 19 июня, 2016 Опубликовано 19 июня, 2016 · Жалоба Пе-ре-мыч-ки. Назовите модель осциллографа, полосу частот, частоту дискретизации. Я умею найти проблемы и в железе и в софте. Не будем меня экзаменовать на этот предмет. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
adnega 11 19 июня, 2016 Опубликовано 19 июня, 2016 · Жалоба ошибку воспроизвести не могу Короче, проверил все с SPI1 по SPI5. Ошибка, увы, не воспроизводится. Читаю-пишу так BYTE spi_send_byte(const BYTE data) { BYTE spib; while((SPI3->SR & (1 << SPI_SR_TXE)) == 0); SPI3->DR = data; while((SPI3->SR & (1 << SPI_SR_RXNE)) == 0); spib = SPI3->DR; return spib; } Пе-ре-мыч-ки. Вопрос определений. Под "резистором 0 Ом" можно понимать: перемычку, резистор, кусок провода, печатную дорожку и т.п. Я покупаю такие; в счете написано "резисторы". Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ViKo 1 19 июня, 2016 Опубликовано 19 июня, 2016 · Жалоба Вопрос определений. Под "резистором 0 Ом" можно понимать: перемычку, резистор, кусок провода, печатную дорожку и т.п. Я покупаю такие; в счете написано "резисторы". Да, вопрос терминологии. Grammar nazi... Пролистал каталог Yageo (верхний из списка http://www.yageo.com/NewPortal/_en/download/download-3.jsp) http://www.yageo.com/exep/pages/download/l..._2016_Final.pdf, и не нашел 0Ω. Где? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Alex11 6 19 июня, 2016 Опубликовано 19 июня, 2016 · Жалоба http://www.yageo.com/NewPortal/_en/search/search-1-1.jsp Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Tarbal 4 19 июня, 2016 Опубликовано 19 июня, 2016 · Жалоба Пе-ре-мыч-ки. Вы можете называть как вам угодно, но их принято называть резисторами. https://www.tu-eshop.com/index.php?route=in...s&news_id=8 http://www.hkresistors.com/-products-zero-ohm-resistor.html Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ViKo 1 19 июня, 2016 Опубликовано 19 июня, 2016 · Жалоба Ага, нашел, jumper. Он еще и точность имеет, и мощность рассеивания. Вы можете называть как вам угодно, но их принято называть резисторами. Я буду называть перемычками, как принято. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Tarbal 4 19 июня, 2016 Опубликовано 19 июня, 2016 · Жалоба Ага, нашел, jumper. Он еще и точность имеет, и мощность рассеивания. Я буду называть перемычками, как принято. :) У меня есть STM32F429I-Disco. Если выложите код, похожий на нерабочий, могу посмотреть. Но с нуля писать лень. Вдруг не не заработает. :rolleyes: Вот такой код. Только теперь вместо нуля всегда читает единицу и только в первом интерфейсе. HAL_StatusTypeDef SPI_WaitOnFlagTimeout(SPI_HandleTypeDef *hspi, uint32_t Flag, FlagStatus Status, uint32_t Timeout) { uint32_t start = jiffies; while(__HAL_SPI_GET_FLAG(hspi, Flag) == Status){ if(jiffies - start >= Timeout){ return -HAL_TIMEOUT; } } return HAL_OK; } #if 0 /* This funtion is used to transmit and receive data * with SPI1 * data --> data to be transmitted * returns received value */ uint8_t SPI1_send(uint8_t data){ SPI1->DR = data; // write data to be transmitted to the SPI data register while( !(SPI1->SR & SPI_I2S_FLAG_TXE) ); // wait until transmit complete while( !(SPI1->SR & SPI_I2S_FLAG_RXNE) ); // wait until receive complete while( SPI1->SR & SPI_I2S_FLAG_BSY ); // wait until SPI is not busy anymore return SPI1->DR; // return received data from SPI data register } #endif int SPI_Transmit1(SPI_HandleTypeDef *hspi, uint8_t* val, uint32_t timeout) { FlagStatus Status; __HAL_SPI_ENABLE(hspi); hspi->Instance->DR = *val; Status = SPI_WaitOnFlagTimeout(hspi, SPI_FLAG_TXE, RESET, timeout); if(HAL_OK != Status){ return Status; } Status = SPI_WaitOnFlagTimeout(hspi, SPI_FLAG_RXNE, RESET, timeout); if(HAL_OK != Status){ return Status; } Status = SPI_WaitOnFlagTimeout(hspi, SPI_FLAG_BSY, SET, timeout); *val = hspi->Instance->DR; return Status; } int write_spi_reg(uint8_t chip_id, uint8_t reg_addr, uint8_t val) { SPI_HandleTypeDef* hspi; uint8_t buf[sPI_WRITE_LEN]; uint8_t i; uint8_t id; GPIO_TypeDef* port; uint16_t pin; HAL_StatusTypeDef ret; if(CHIPS_AMOUNT <= chip_id){ return -WRONG_PARAMETER; } hspi = hspi1; id = 0 port = GPIOA; pin = GPIO_PIN_4; buf[0] = WR_SPI_CMD(id); buf[1] = reg_addr; buf[2] = val; for(i = 0; i < SPI_WRITE_LEN; i++){ HAL_GPIO_WritePin(port, pin, 0); short_delay(7); ret = SPI_Transmit1(hspi, &buf[i], SPI_TIMEOUT); HAL_GPIO_WritePin(port, pin, 1); short_delay(7); if(HAL_OK != ret){ responce_handle(ret); return -ret; } } return NO_ERROR; } int read_spi_reg(uint8_t chip_id, uint8_t reg_addr) { SPI_HandleTypeDef* hspi; uint8_t buf[2]; uint8_t id; HAL_StatusTypeDef ret; GPIO_TypeDef* port; uint16_t pin; chip_interface_t* chip_if; if(CHIPS_AMOUNT <= chip_id){ return; } hspi = hspi1; id = 0 port = GPIOA; pin = GPIO_PIN_4; buf[0] = RD_SPI_CMD(id); buf[1] = reg_addr; HAL_GPIO_WritePin(port, pin, 0); short_delay(7); ret = SPI_Transmit1(hspi, &buf[0], SPI_TIMEOUT); HAL_GPIO_WritePin(port, pin, 1); short_delay(7); HAL_GPIO_WritePin(port, pin, 0); short_delay(7); ret = SPI_Transmit1(hspi, &buf[1], SPI_TIMEOUT); HAL_GPIO_WritePin(port, pin, 1); short_delay(7); if(HAL_OK != ret){ responce_handle(ret); return (uint16_t) -1; } HAL_GPIO_WritePin(port, pin, 0); short_delay(7); ret = SPI_Transmit1(hspi, &buf[0], SPI_TIMEOUT); HAL_GPIO_WritePin(port, pin, 1); short_delay(7); if(HAL_OK != ret){ responce_handle(ret); } return (uint32_t)buf[0]; } Конфигурация: Registers SPI_CR1 = 0x0000015F SPI_CR2 = 0x00000004 Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Tarbal 4 20 июня, 2016 Опубликовано 20 июня, 2016 · Жалоба А замена на такую функцию (без аппаратной поддержки SPI) прекрасно работает. #define PIN(PORT, PIN) GPIO##PORT, GPIO_PIN_##PIN #define SPI1_CLK_PIN PIN(B, 3) #define SPI1_MOSI_PIN PIN(A,7) #define SPI1_MISO_PIN PIN(A, 6) #define SPI1_SS_PIN PIN(A, 4) #define SET_CLK1() HAL_GPIO_WritePin(SPI1_CLK_PIN, 1) #define CLR_CLK1() HAL_GPIO_WritePin(SPI1_CLK_PIN, 0) #define SET_MOSI1() HAL_GPIO_WritePin(SPI1_MOSI_PIN, 1) #define CLR_MOSI1() HAL_GPIO_WritePin(SPI1_MOSI_PIN, 0) #define GET_MISO1() HAL_GPIO_ReadPin(SPI1_MISO_PIN) int SPI_Transmit1(SPI_HandleTypeDef *hspi, uint8_t* val, uint32_t timeout) { int i; uint8_t res= 0, tmp = *val; if(&hspi1 == hspi){ for(i = 0; i < 8; i++){ res <<= 1; CLR_CLK1(); if(tmp & 0x80){ SET_MOSI1(); } else { CLR_MOSI1(); } res |= GET_MISO1(); SET_CLK1(); tmp <<= 1; } } else { return SPI_Transmit1_hw(hspi, val, timeout); } *val = res; return 0; } В принципе если ожидать в цикле флагов, аппаратное исполнение не дает выигрыша, ну разве только на выскоких частотах обмена. Программное исполнение дает клок 1 мегагерц, что довольно сносно. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ViKo 1 20 июня, 2016 Опубликовано 20 июня, 2016 · Жалоба С HAL мучайтесь сами, мне это не интересно. У меня свой HAL. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Tarbal 4 20 июня, 2016 Опубликовано 20 июня, 2016 · Жалоба С HAL мучайтесь сами, мне это не интересно. У меня свой HAL. Да вроде ключевые моменты не на HAL. Разве только ножкой подрыгать не переписал. Да и не надо проверять. Я уже все исследовал сам. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ViKo 1 20 июня, 2016 Опубликовано 20 июня, 2016 · Жалоба Я уже все исследовал сам. И какие же выводы от исследований? "Кто был охотник, кто добыча?" SPI-то работает или где? В первом интерфейсе читает единицу, а в других что? А должен что читать? :rolleyes: Какие-то невнятные сообщения. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Tarbal 4 21 июня, 2016 Опубликовано 21 июня, 2016 · Жалоба И какие же выводы от исследований? "Кто был охотник, кто добыча?" SPI-то работает или где? В первом интерфейсе читает единицу, а в других что? А должен что читать? :rolleyes: Какие-то невнятные сообщения. Программная имплементация SPI работает без проблем, что подтверждает, что во внешних цепях SPI все правильно. На форуме ST проблема младшего бита именно в SPI1 возникала много раз. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться