Перейти к содержанию

STM32F103C8T6 W25Q32 USB Флешка Не работает


artos5

Рекомендуемые сообщения

 

Добрый день!
В просторах интернета нашел проект: https://github.com/pav2000/USB_W25Q32
А также темы , в которых у людей тоже возникали проблемы:
https://electronics.stackexchange.com/questions/494692/stm32f103c8-w25q64-usb-mass-storage-device

http://forum.easyelectronics.ru/viewtopic.php?f=35&t=42411

Я скачал проект, пересобрал под микроконтроллер STM32F103C8, и прошил.
В результате не работает. Даже на этапе форматирования возникает сбой.
У кого есть рабочий проект для такого МК и флешки? Либо кто может помочь?

Может быть проблема в размере блока 1024 байта? Система не хочет ставить размер блока меньше чем 1024, а в проекте размер блока 512....

 

/*---------- -----------*/
#define USBD_MAX_NUM_INTERFACES     1
/*---------- -----------*/
#define USBD_MAX_NUM_CONFIGURATION     1
/*---------- -----------*/
#define USBD_MAX_STR_DESC_SIZ    512
/*---------- -----------*/
#define USBD_DEBUG_LEVEL     0
/*---------- -----------*/
#define USBD_SELF_POWERED     1
/*---------- -----------*/
#define MSC_MEDIA_PACKET     512

 

void w25qWritingByUSB(uint16_t dpagenum, uint8_t *bufByUSB) {

    uint8_t current_sector_buf[4096];
    uint16_t current_sector_addr = dpagenum / 8;
    uint16_t startPage = current_sector_addr * 16;
    int offset = 512 * (dpagenum % 8);

    for (uint16_t i = 0; i < 16; i++) {
        w25qReadPage(current_sector_buf + 256 * i, startPage + i);
    }

    memcpy(current_sector_buf + offset, bufByUSB, 512);

    w25qEraseSector(current_sector_addr);

    startPage = current_sector_addr * 16;

    for (uint16_t i = 0; i < 16; i++) {
        uint8_t buf[256];
        memcpy(buf, current_sector_buf + i * 256, 256);
        w25qWritePage(buf, startPage + i);
    }
}

 

void _w25qEraseSector(uint32_t sector) {
   w25qSetBlockProtect(0x00);
   sector = (sector << 4);  // Отличие

   uint8_t com = W25Q_WRITE_ENABLE;
   uint8_t temp[4] = { W25Q_SECTOR_ERASE_4, (uint8_t) (sector >> 8),
         (uint8_t) (sector & 0x00FF), 0x00 };

   W25Q_CS_LO();
   //HAL_SPI_Transmit(W25Q_SPI, &com, 1, 10);
				 SPI_Send(com);
   W25Q_CS_HI();

   W25Q_CS_LO();
   //HAL_SPI_Transmit(W25Q_SPI, temp, 4, 10);
				for(uint8_t x=0; x<4; x++) SPI_Send(temp[x]);
   W25Q_CS_HI();

   w25qWaitForReady();

   temp[0] = W25Q_WRRITE_DISABLE;

   W25Q_CS_LO();
   //HAL_SPI_Transmit(W25Q_SPI, temp, 1, 10);
				  SPI_Send(temp[0]);
   W25Q_CS_HI();

   w25qSetBlockProtect(0x0F);
}


 

И еще, как переделать под размер блока 1024? Кроме дефайнов что еще поправить? Потому как проблема также есть, но статусный светодиод иначе ведет себя.

Что может быть лучше в радиоэлектронике, чем программирование микроконтроллеров ?

Ссылка на комментарий
Поделиться на другие сайты

Реклама: ООО ТД Промэлектроника, ИНН: 6659197470, Тел: 8 (800) 1000-321

Сейчас разбираюсь с адресами, что-то у автора похоже напутано с адресами....
Какой диапазон значений у dpagenum для флешки 4МБ. такой ( 4МБ / 1024 )?:

void w25qWritingByUSB(uint16_t dpagenum, uint8_t *bufByUSB)

и какой диапазон значений у sector?:
 

_w25qEraseSector(uint32_t sector)

загнал этот код в Visual studio
и получаю такое:
при значении от 0 до 7 

в _w25qEraseSector(uint32_t sector) попадает 0

при значении от 8 до 15

в _w25qEraseSector(uint32_t sector) попадает 1

при значении от 16 до 23

в _w25qEraseSector(uint32_t sector) попадает 2

и т.д.
1032473594_2024-03-26170303.png.01d968658bf88430363be6953eafab80.png

Код Visual studio:

Спойлер
#include <iostream>
#include <stdio.h>
#include "windows.h"

uint32_t sector = 0;
uint16_t dpagenum = 0;

// Команды
#define W25Q_WRITE_ENABLE       0X06
#define W25Q_WRRITE_DISABLE     0X04
#define W25Q_RD_STATUS_1        0x05       
#define W25Q_RD_STATUS_2        0x35
#define W25Q_WR_STATUS          0x01
#define W25Q_PAGE_PROGRAM       0x02
#define W25Q_Q_PAGE_PROGRAM     0x32
#define W25Q_BLOCK_ERASE_64     0xD8
#define W25Q_BLOCK_ERASE_32     0x52
#define W25Q_SECTOR_ERASE_4     0x20
#define W25Q_CHIP_ERASE         0xC7
#define W25Q_ERASE_SUSPEND      0X75
#define W25Q_ERASE_RESUME       0x7A
#define W25Q_POWER_DOWN         0xB9
#define W25Q_HI_PF_MODE         0xA3
#define W25Q_MODE_BIT_RESET     0xFF
#define W25Q_RS_PWR_DOUN        0xAB
#define W25Q_MNF_DEVICE_ID      0x90
#define W25Q_RD_UNIQUE_ID       0x4B
#define W25Q_JEDEC_ID           0x9F
#define W25Q_READ_PAGE          0x0B

void _w25qEraseSector(uint32_t sector) {
    //w25qSetBlockProtect(0x00);
    printf("Sectors ADDR=%X\n", sector);
    sector = (sector << 4);  // Отличие

    uint8_t com = W25Q_WRITE_ENABLE;
    uint8_t temp[4] = { W25Q_SECTOR_ERASE_4, (uint8_t)(sector >> 8),
          (uint8_t)(sector & 0x00FF), 0x00 };

    //W25Q_CS_LO();
    //HAL_SPI_Transmit(W25Q_SPI, &com, 1, 10);
    //printf("&COM %02X\n\n", &com);//SPI_Send(com);
   // W25Q_CS_HI();

    //W25Q_CS_LO();
    //HAL_SPI_Transmit(W25Q_SPI, temp, 4, 10);
    printf("DATA SECTOR:\n");
    for (uint8_t x = 0; x < 4; x++) printf("%02X ", temp[x]); //SPI_Send(temp[x]);
    printf("\n");
    //W25Q_CS_HI();

   // w25qWaitForReady();

    temp[0] = W25Q_WRRITE_DISABLE;

    //W25Q_CS_LO();
    //HAL_SPI_Transmit(W25Q_SPI, temp, 1, 10);
    printf("%02X\n", temp[0]); //SPI_Send(temp[0]);
   // W25Q_CS_HI();

    //w25qSetBlockProtect(0x0F);
}

int main() {

    SetConsoleCP(1251);
    SetConsoleOutputCP(1251);
    setlocale(LC_ALL, "RU");
    while (1)
    {
        printf("Введите номер сектора:\n");
        scanf_s("%d", &dpagenum);

        uint8_t current_sector_buf[4096];
        uint16_t current_sector_addr = dpagenum / 8;
        uint16_t startPage = current_sector_addr * 16;
        int offset = 512 * (dpagenum % 8);

        _w25qEraseSector(current_sector_addr);
    }
    return 0;
}

 

 

 

Что может быть лучше в радиоэлектронике, чем программирование микроконтроллеров ?

Ссылка на комментарий
Поделиться на другие сайты

20% скидка на весь каталог электронных компонентов в ТМ Электроникс!

Акция "Лето ближе - цены ниже", успей сделать выгодные покупки!

Плюс весь апрель действует скидка 10% по промокоду APREL24 + 15% кэшбэк и бесплатная доставка!

Перейти на страницу акции

Реклама: ООО ТМ ЭЛЕКТРОНИКС, ИНН: 7806548420, info@tmelectronics.ru, +7(812)4094849

Получается 64 блока в которых 16 секторов и 4096 байт в секторе. Итого секторов: 1024 для W25Q32.

Осталось разобраться какой диапазон значений у "void w25qWritingByUSB(uint16_t dpagenum, uint8_t *bufByUSB)"

А именно у dpagenum.
Подскажите пожалуйста кто знает... Это сильно сократит время.

Что может быть лучше в радиоэлектронике, чем программирование микроконтроллеров ?

Ссылка на комментарий
Поделиться на другие сайты

Выбираем схему BMS для корректной работы литий-железофосфатных (LiFePO4) аккумуляторов

 Обязательным условием долгой и стабильной работы Li-FePO4-аккумуляторов, в том числе и производства EVE Energy, является применение специализированных BMS-микросхем. Литий-железофосфатные АКБ отличаются такими характеристиками, как высокая многократность циклов заряда-разряда, безопасность, возможность быстрой зарядки, устойчивость к буферному режиму работы и приемлемая стоимость. Но для этих АКБ, также как и для других, очень важен контроль процесса заряда и разряда, а специализированных микросхем для этого вида аккумуляторов не так много. Инженеры КОМПЭЛ подготовили список имеющихся микросхем и возможных решений от разных производителей. Подробнее>>

Реклама: АО КОМПЭЛ, ИНН: 7713005406, ОГРН: 1027700032161

Хорошие новости всегда радуют. Напишите пожалуйста, в чем была у вас проблема?

Что поправили, что бы ваш проект заработал?

Елси это возможно - поделитесь пожалуйста рабочим проектом на почту antonslobodchuk@gmail.com

Спасибо!

Ссылка на комментарий
Поделиться на другие сайты

Я в ходе отладки выяснил, что сбоит в функции: 

void w25qWritingByUSB(uint32_t dpagenum, uint8_t *bufByUSB)

При чем поведение очень странное. Отладочные сообщения даже не выводятся в начале функции.
В ходе экспериментов понял что связано это с объявлением массивов и решил объявить большие буферы которые на 4КБ и 0.25КБ:

    uint8_t current_sector_buf[4096];
		uint8_t buf[256];

глобально.
В оригинале, буферы объявлялись локально в функции. После изменения буквально двух строчек кода, все заработало.
Также, в оригинальном проекте было сильно напутано из функциями. Я решил функции выкинуть из main.c и вставить в w25q.c
Эти функции:

void w25qEraseSector(uint16_t sector)
void w25qWritingByUSB(uint32_t dpagenum, uint8_t *bufByUSB)

Поиск данной проблемы реально отобрало кучу времени. На будущее буду знать что и такое бывает...

Что может быть лучше в радиоэлектронике, чем программирование микроконтроллеров ?

Ссылка на комментарий
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.
Примечание: Ваш пост будет проверен модератором, прежде чем станет видимым.

Гость
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Ответить в этой теме...

×   Вставлено с форматированием.   Восстановить форматирование

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

Загрузка...
  • Последние посетители   0 пользователей онлайн

    • Ни одного зарегистрированного пользователя не просматривает данную страницу
×
×
  • Создать...