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

Ещё раз прошу помощи у Умов по поводу своей писанины. Переделал плату, поставил stm32f429b 208ногий и sdram is42s16800 - 16Мб, произвёл успешную инициализацию всех модулей с помощью cube (уж извиняюсь за ламерство, но уж слишком много всего инициализировать).

Инициализировал видеобуфер на sdram (0xD0000000), вроде бы даже заполнил нужные области и вывел текст.

DSC_0146.jpg

Но микроконтроллер постоянно прижимает резет, картинка выводится, но дёргается, заливается с искажениями. Аппаратно всё проверил, перепаял все пины и конденсаторы.

DSC_0147.jpg

Когда отключаю инициализацию буфера слоя экрана - резеты прекращаются.

Частота микроконтроллера - 168 Мгц

тайминги озу следующие

image.jpg

 

Код инициализации SDRAM

void MX_FMC_Init(void)
{
 FMC_SDRAM_TimingTypeDef SdramTiming;

 /** Perform the SDRAM1 memory initialization sequence
// 168/2= 84 MHz, 
 */
 hsdram1.Instance = FMC_SDRAM_DEVICE;
 /* hsdram1.Init */
 hsdram1.Init.SDBank = FMC_SDRAM_BANK2;
 hsdram1.Init.ColumnBitsNumber = FMC_SDRAM_COLUMN_BITS_NUM_8;
 hsdram1.Init.RowBitsNumber = FMC_SDRAM_ROW_BITS_NUM_12;
 hsdram1.Init.MemoryDataWidth = FMC_SDRAM_MEM_BUS_WIDTH_16;
 hsdram1.Init.InternalBankNumber = FMC_SDRAM_INTERN_BANKS_NUM_4;
 hsdram1.Init.CASLatency = FMC_SDRAM_CAS_LATENCY_2;
 hsdram1.Init.WriteProtection = FMC_SDRAM_WRITE_PROTECTION_DISABLE;
 hsdram1.Init.SDClockPeriod = FMC_SDRAM_CLOCK_PERIOD_2;
 hsdram1.Init.ReadBurst = FMC_SDRAM_RBURST_DISABLE;
 hsdram1.Init.ReadPipeDelay = FMC_SDRAM_RPIPE_DELAY_1;
 /* SdramTiming */
 SdramTiming.LoadToActiveDelay = 0x02;				//TMRD
 SdramTiming.ExitSelfRefreshDelay = 0x06;		//TXSR
 SdramTiming.SelfRefreshTime = 0x04;		//TRAS
 SdramTiming.RowCycleDelay = 0x06;			//TRC>TRFC
 SdramTiming.WriteRecoveryTime = 0x02;	//TWR, TWR>=TRAS-TRCD, TWR>=TRC-TRCD-TRP
 SdramTiming.RPDelay = 0x02;		// TRP
 SdramTiming.RCDDelay = 0x02;	// TRCD

 if (HAL_SDRAM_Init(&hsdram1, &SdramTiming) != HAL_OK)
 {
Error_Handler();
 }
/* Program the SDRAM external device */

 SDRAM_Initialization_Sequence(&hsdram1, &command); 
}

void SDRAM_Initialization_Sequence(SDRAM_HandleTypeDef *hsdram, FMC_SDRAM_CommandTypeDef *Command)
{
 __IO uint32_t tmpmrd =0;
 /* Step 3:  Configure a clock configuration enable command */
 Command->CommandMode 			 = FMC_SDRAM_CMD_CLK_ENABLE;
 Command->CommandTarget 		 = FMC_SDRAM_CMD_TARGET_BANK2;
 Command->AutoRefreshNumber 	 = 1;
 Command->ModeRegisterDefinition = 0;

 /* Send the command */
 HAL_SDRAM_SendCommand(hsdram, Command, 0x1000);

 /* Step 4: Insert 100 ms delay */
 HAL_Delay(100);

 /* Step 5: Configure a PALL (precharge all) command */ 
 Command->CommandMode 			 = FMC_SDRAM_CMD_PALL;
 Command->CommandTarget 		 = FMC_SDRAM_CMD_TARGET_BANK2;
 Command->AutoRefreshNumber 	 = 1;
 Command->ModeRegisterDefinition = 0;

 /* Send the command */
 HAL_SDRAM_SendCommand(hsdram, Command, 0x1000);  

 /* Step 6 : Configure a Auto-Refresh command */ 
 Command->CommandMode 			 = FMC_SDRAM_CMD_AUTOREFRESH_MODE;
 Command->CommandTarget 		 = FMC_SDRAM_CMD_TARGET_BANK2;
 Command->AutoRefreshNumber 	 = 4;
 Command->ModeRegisterDefinition = 0;

 /* Send the command */
 HAL_SDRAM_SendCommand(hsdram, Command, 0x1000);

 /* Step 7: Program the external memory mode register */
 tmpmrd = (uint32_t)SDRAM_MODEREG_BURST_LENGTH_2		  |
				 SDRAM_MODEREG_BURST_TYPE_SEQUENTIAL   |
				 SDRAM_MODEREG_CAS_LATENCY_2		   |
				 SDRAM_MODEREG_OPERATING_MODE_STANDARD |
				 SDRAM_MODEREG_WRITEBURST_MODE_SINGLE;

 Command->CommandMode = FMC_SDRAM_CMD_LOAD_MODE;
 Command->CommandTarget 		 = FMC_SDRAM_CMD_TARGET_BANK2;
 Command->AutoRefreshNumber 	 = 1;
 Command->ModeRegisterDefinition = tmpmrd;

 /* Send the command */
 HAL_SDRAM_SendCommand(hsdram, Command, 0x1000);

 /* Step 8: Set the refresh rate counter */
 /* (15.62 us x Freq) - 20 */
 /* Set the device refresh counter */
 HAL_SDRAM_ProgramRefreshRate(hsdram, 1542); 
HAL_SDRAM_ProgramRefreshRate(hsdram, 671); 
}

 

Работаю с памятью напрямую, без dma

 

void LCD_PutPixel (uint16_t x, uint16_t y, uint16_t color)
{
    TM_SDRAM_Write16((x+y*LCD_LAYER1_WIDTH)*2, color);
}

 

 

Уже всё голову в кровь разбил, перечитал кучу тем, а собрать всё воедино не получается.

Может ошибка в инициализации sdram- использовал примеры для discovery с адаптацией под свою плату(там 8Мб, а у меня -- 16), но не пойму, где именно. Может встречался кто-то с подобной проблемой, или просто у кого мысли есть - был бы признателен.

 

PS. Перепаял IS42 на микросхему с Discovery, перенастроил тайминги, результат аналогичный(

Изменено пользователем IgorKossak
[codebox] для длинного кода, [code] - для короткого!

Поделиться сообщением


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

Подскажите софтину для преобразования картинки в ARGB4444

 

adrvyho

1. Попробуйте выводить картинку из флешки напрямую без участия SDRAM или просто однотонный фон, для этого даже картинка не нужна.

2. В дебаггере посмотрите не меняется ли содержимое SDRAM. KEIL+JLINK позволяют просматривать содержимое SDRAM, даже данные на лету обновляются.

Поделиться сообщением


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

Уже всё голову в кровь разбил

Тест памяти делали? Как по мне, то первое, что нужно сделать это прогнать хотя бы минимальный тест SDRAM, чтобы иметь хоть какую-то уверенность, что она работает нормально. И еще питание гляньте не просаживается ли. Ведь при включении дисплея потребление и памятью и МК подрастет - может его тупо не хватает, вот он и сбрасывается.

Поделиться сообщением


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

Подскажите софтину для преобразования картинки в ARGB4444

Скачивал в своё время несколько программ для конвертации - Display's module image converter, Image2Code, Bitmap Converter, но ни в одной не видел ARGB4444 - сам использую RGB565

1. Попробуйте выводить картинку из флешки напрямую без участия SDRAM или просто однотонный фон, для этого даже картинка не нужна.

Модуль LTDC был проверен первым делом - background заливается без искажений нужным цветом, слои активируются в тех габаритах, как говорят.

С flash на этой плате не запускал, только на предыдущей - слишком уж долго программа прошивается)

2. В дебаггере посмотрите не меняется ли содержимое SDRAM. KEIL+JLINK позволяют просматривать содержимое SDRAM, даже данные на лету обновляются.

Дебагер, к сожалению, обрывается, видимо из-за резетов в линии (это если видеобуфер объявлен в LTDC, без него в линии все прекрасно). Вывел на экран инкремент переменной раз в секунду - плюсуется 32 раза и выводится восьмёрка и залитый символ (при этом резеты присутствуют);дежурный светодиод при этом продолжает мерцать раз в секунду. Какая-то чертовщина, короче - резеты в линии, при этом картинка из SDRAM выводится практически идеально(присутствуют небольшие побочки), текст и числа на экран выводятся, переменная инкрементируется 32 раза, но при этом не обнуляется (то есть вроде как программа не перезапускается). Покопался в errdata, ревизия контроллера 3, если не ошибаюсь (ID 0x2BA01477), так что по идее, проблем с FMC и обращением к динамической, а потом статической памяти быть не должно...

 

Поделиться сообщением


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

Тест памяти делали? Как по мне, то первое, что нужно сделать это прогнать хотя бы минимальный тест SDRAM, чтобы иметь хоть какую-то уверенность, что она работает нормально. И еще питание гляньте не просаживается ли. Ведь при включении дисплея потребление и памятью и МК подрастет - может его тупо не хватает, вот он и сбрасывается.

Тест памяти делаю после инициализации - заполняю буфер Tx, перевожу его в SDRAM, считываю, сравниваю - не проходит, дэбагер при отключенном указателе на видеобуфер запускается, в SDRAM следующая картина

 

123.jpg

То есть, вроде как всё заполняется, но то тут, то там соскакивают ячейки, потом восстанавливаются.

Напряжение 3,282-3,298В, сила тока 0,4 А при включенном экране, контроллере и SDRAM, что для микросхемы-стабилизатора TPS63060 - треть нагрузки

 

 

Поделиться сообщением


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

Какая частота AHB?

Покажите настройки FMC.

Покажите SDRAM_Initialization_sequence()

 

резеты в линии
Что это значит и как определяете?

Поделиться сообщением


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

Что это значит и как определяете?

:biggrin: Я тоже не понял... Какие ресеты в какой линии... Причём здесь LTDC... Одни вопросы.

Неверная настройка самого контроллера по частотам к краху приводить не должна. Если не так области заданы, ну тогда наверное возможно... Ну типа видеоозу не по тем адресам задано.... Тогда наверное при попытке обращения будет вызываться немаскируемое прерывание и рестарт... Ну так там надо просто посмотреть... Да и всё.

Поделиться сообщением


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

Какая частота AHB?

Частота AHB 168 МГц

Покажите настройки FMC.

Настройки я как только не менял, даже научным перебором попробовал). То, что осталось от моих рвений:

void MX_FMC_Init(void)
{
 FMC_SDRAM_TimingTypeDef SdramTiming;

 /** Perform the SDRAM1 memory initialization sequence
// 168/2= 84 MHz, 
 */
 hsdram1.Instance = FMC_SDRAM_DEVICE;
 /* hsdram1.Init */
 hsdram1.Init.SDBank = FMC_SDRAM_BANK2;
 hsdram1.Init.ColumnBitsNumber = FMC_SDRAM_COLUMN_BITS_NUM_8;
 hsdram1.Init.RowBitsNumber = FMC_SDRAM_ROW_BITS_NUM_12;
 hsdram1.Init.MemoryDataWidth = FMC_SDRAM_MEM_BUS_WIDTH_16;
 hsdram1.Init.InternalBankNumber = FMC_SDRAM_INTERN_BANKS_NUM_4;
 hsdram1.Init.CASLatency = FMC_SDRAM_CAS_LATENCY_3;
 hsdram1.Init.WriteProtection = FMC_SDRAM_WRITE_PROTECTION_DISABLE;
 hsdram1.Init.SDClockPeriod = FMC_SDRAM_CLOCK_PERIOD_2;
 hsdram1.Init.ReadBurst = FMC_SDRAM_RBURST_ENABLE;
 hsdram1.Init.ReadPipeDelay = FMC_SDRAM_RPIPE_DELAY_2;
 /* SdramTiming */
 SdramTiming.LoadToActiveDelay = 0x02;				//TMRD
 SdramTiming.ExitSelfRefreshDelay = 0x07;		//TXSR
 SdramTiming.SelfRefreshTime = 0x04;		//TRAS
 SdramTiming.RowCycleDelay = 0x07;			//TRC>TRFC
 SdramTiming.WriteRecoveryTime = 0x03;	//TWR, TWR>=TRAS-TRCD, TWR>=TRC-TRCD-TRP
 SdramTiming.RPDelay = 0x02;		// TRP
 SdramTiming.RCDDelay = 0x02;	// TRCD

 if (HAL_SDRAM_Init(&hsdram1, &SdramTiming) != HAL_OK)
 {
Error_Handler();
 }
/* Program the SDRAM external device */

 SDRAM_Initialization_Sequence(&hsdram1, &command); 


 /* Write data to the SDRAM memory */
 for (uwIndex = 0; uwIndex < BUFFER_SIZE; uwIndex++)
{
	aTxBuffer[uwIndex]=0xA102;

	*(uint32_t*) (SDRAM_BANK_ADDR + uwIndex*2)=aTxBuffer[uwIndex];
	for (uint16_t ii=0;ii<10;ii++);
}
HAL_SDRAM_Read_16b(&hsdram1, (uint32_t*)SDRAM_BANK_ADDR, aTxBuffer, BUFFER_SIZE);


 /* Read back data from the SDRAM memory */

 for (uwIndex = 0; uwIndex < BUFFER_SIZE; uwIndex++)
 {
	aRxBuffer[uwIndex] =*(uint32_t*) (SDRAM_BANK_ADDR + uwIndex*2);
  } 

//HAL_SDRAM_Write_16b(&hsdram1, (uint32_t*)SDRAM_BANK_ADDR, aRxBuffer, BUFFER_SIZE);
HAL_Delay (10);

 /*##-3- Checking data integrity ############################################*/	


 for (uwIndex = 0; (uwIndex < BUFFER_SIZE) && (uwWriteReadStatus == 0); uwIndex++)
 {
if (aRxBuffer[uwIndex] != aTxBuffer[uwIndex])
{
  uwWriteReadStatus++;
}

 }	

 if (uwWriteReadStatus)
 {
/* KO */
HAL_GPIO_WritePin(GPIOB, GPIO_PIN_15,1);	 
 }
 else
 { 
/* OK */
 }


}

 

Покажите SDRAM_Initialization_sequence()

 

void SDRAM_Initialization_Sequence(SDRAM_HandleTypeDef *hsdram, FMC_SDRAM_CommandTypeDef *Command)
{
 __IO uint32_t tmpmrd =0;
 /* Step 3:  Configure a clock configuration enable command */
 Command->CommandMode 			 = FMC_SDRAM_CMD_CLK_ENABLE;
 Command->CommandTarget 		 = FMC_SDRAM_CMD_TARGET_BANK2;
 Command->AutoRefreshNumber 	 = 1;
 Command->ModeRegisterDefinition = 0;

 /* Send the command */
 HAL_SDRAM_SendCommand(hsdram, Command, 0x1000);

 /* Step 4: Insert 100 ms delay */
 HAL_Delay(100);

 /* Step 5: Configure a PALL (precharge all) command */ 
 Command->CommandMode 			 = FMC_SDRAM_CMD_PALL;
 Command->CommandTarget 		 = FMC_SDRAM_CMD_TARGET_BANK2;
 Command->AutoRefreshNumber 	 = 1;
 Command->ModeRegisterDefinition = 0;

 /* Send the command */
 HAL_SDRAM_SendCommand(hsdram, Command, 0x1000);  

 /* Step 6 : Configure a Auto-Refresh command */ 
 Command->CommandMode 			 = FMC_SDRAM_CMD_AUTOREFRESH_MODE;
 Command->CommandTarget 		 = FMC_SDRAM_CMD_TARGET_BANK2;
 Command->AutoRefreshNumber 	 = 8;
 Command->ModeRegisterDefinition = 0;

 /* Send the command */
 HAL_SDRAM_SendCommand(hsdram, Command, 0x1000);

 /* Step 7: Program the external memory mode register */
 tmpmrd = (uint32_t)SDRAM_MODEREG_BURST_LENGTH_2		  |
				 SDRAM_MODEREG_BURST_TYPE_SEQUENTIAL   |
				 SDRAM_MODEREG_CAS_LATENCY_3		   |
				 SDRAM_MODEREG_OPERATING_MODE_STANDARD |
				 SDRAM_MODEREG_WRITEBURST_MODE_SINGLE;

 Command->CommandMode = FMC_SDRAM_CMD_LOAD_MODE;
 Command->CommandTarget 		 = FMC_SDRAM_CMD_TARGET_BANK2;
 Command->AutoRefreshNumber 	 = 1;
 Command->ModeRegisterDefinition = tmpmrd;

 /* Send the command */
 HAL_SDRAM_SendCommand(hsdram, Command, 0x1000);

 /* Step 8: Set the refresh rate counter */
 /* (15.62 us x Freq) - 20 */
 /* Set the device refresh counter */
 HAL_SDRAM_ProgramRefreshRate(hsdram, 0x0569); 
}

Что это значит и как определяете?

Пардоньте за жаргон. Резетами в линии я называю импульсы низкого уровня на линии reset микроконтроллера. Смотрю осциллоскопом (фото выше прилагал). То есть, когда я включаю инициализацию видеобуфера - с периодичностью 20 мс линия reset прижимается к земле; выключаю объявление видеобуфера - в линии reset спокойные 3.3В

 

 

:biggrin: Я тоже не понял... Какие ресеты в какой линии... Причём здесь LTDC... Одни вопросы.

Неверная настройка самого контроллера по частотам к краху приводить не должна. Если не так области заданы, ну тогда наверное возможно... Ну типа видеоозу не по тем адресам задано.... Тогда наверное при попытке обращения будет вызываться немаскируемое прерывание и рестарт... Ну так там надо просто посмотреть... Да и всё.

Хорошая мысль! Тоже думал, будто видеобуфер добегает до конца, стукается об стенку и перезагружается)) (уж извиняюсь, с помощью простых аналогий пытаюсь понять суть сложных вещей).

На всякий случай вот код инициализации экрана, может здесь, конечно, накосячил

#define LCD_LAYER1_WIDTH		790
#define LCD_LAYER1_HEIGHT	   470

void MX_LTDC_Init(void)
{
 LTDC_LayerCfgTypeDef pLayerCfg;
 LTDC_LayerCfgTypeDef pLayerCfg1;

 hltdc.Instance = LTDC;
 hltdc.Init.HSPolarity = LTDC_HSPOLARITY_AL;
 hltdc.Init.VSPolarity = LTDC_VSPOLARITY_AL;
 hltdc.Init.DEPolarity = LTDC_DEPOLARITY_AL;
 hltdc.Init.PCPolarity = LTDC_PCPOLARITY_IPC;
 hltdc.Init.HorizontalSync = 47;
 hltdc.Init.VerticalSync = 2;
 hltdc.Init.AccumulatedHBP = 87;
 hltdc.Init.AccumulatedVBP = 31;
 hltdc.Init.AccumulatedActiveW = 887;
 hltdc.Init.AccumulatedActiveH = 511;
 hltdc.Init.TotalWidth = 927;
 hltdc.Init.TotalHeigh = 524;
 hltdc.Init.Backcolor.Blue = 255;
 hltdc.Init.Backcolor.Green = 255;
 hltdc.Init.Backcolor.Red = 255;
 if (HAL_LTDC_Init(&hltdc) != HAL_OK)
 {
Error_Handler();
 }

 pLayerCfg.WindowX0 = 5;
 pLayerCfg.WindowX1 = 795;
 pLayerCfg.WindowY0 = 5;
 pLayerCfg.WindowY1 = 475;
 pLayerCfg.PixelFormat = LTDC_PIXEL_FORMAT_RGB565;
 pLayerCfg.Alpha = 255;
 pLayerCfg.Alpha0 = 0;
 pLayerCfg.BlendingFactor1 = LTDC_BLENDING_FACTOR1_CA;
 pLayerCfg.BlendingFactor2 = LTDC_BLENDING_FACTOR2_CA;
 pLayerCfg.FBStartAdress =(uint32_t)0xD0000000;
 pLayerCfg.ImageWidth = LCD_LAYER1_WIDTH;
 pLayerCfg.ImageHeight = LCD_LAYER1_HEIGHT;
 pLayerCfg.Backcolor.Blue = 0;
 pLayerCfg.Backcolor.Green = 0;
 pLayerCfg.Backcolor.Red = 255;

 if (HAL_LTDC_ConfigLayer(&hltdc, &pLayerCfg, 0) != HAL_OK)
 {
Error_Handler();
 }

}

Изменено пользователем IgorKossak
[codebox] для длинного кода, [code] - для короткого!

Поделиться сообщением


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

то есть, когда я включаю инициализацию видеобуфера - с периодичностью 20 мс линия reset прижимается к земле; выключаю объявление видеобуфера - в линии reset спокойные 3.3В
Вы пишите об этом так как-будто это в порядке вещей. Разбирайтесь кто там напряжение просаживает.

Поделиться сообщением


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

Вы пишите об этом так как-будто это в порядке вещей. Разбирайтесь кто там напряжение просаживает.

Дело в том, что при наличии и отсутствии строчки

pLayerCfg.FBStartAdress =(uint32_t)0xD0000000;

ситуации следующие:

При отсутствующей:

Напряжение питания

 

DSC_0172.jpg

DSC_0169.jpg

 

Линия reset

 

DSC_0171.jpg

DSC_0170.jpg

 

При наличии строчки питание абсолютно не проседает, не прыгает, всё те же 3,301В, а в линии reset следующая картина:

 

DSC_0174.jpg

 

Попробовал адресовать видеобуфер на внутреннюю память - в линии reset всё спокойно, картинка отображается как надо.

SDRAM выпаяна с STM32F429Discovery, подключена к контроллеру также. Стоит ли грешить на разводку платы- уж думаю, не влияет ли то, что микросхема sdram находиться под микроконтроллером, с обратной стороны платы?...

 

Поделиться сообщением


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

Позвоните ресет с соседними ногами.

Рядом сигнал FMC_SDNWE

В точку!!!

Огромное спасибо!!! ЧтоГдеКогда отдыхает! Лучшего подарка на день рождения я и придумать не мог!!!))

Reset действительно звонится с sdnwe, причем контроллер припаян нормально, видимо косяк платы, причём где-то под микроконтроллером)))

А может ли в самом контролере замкнуть соседние ноги?

 

Ура!!!! Заработало!!!! Дело было в косяке платы, слава богу, что контактов, а не переходного отверстия, что под микроконтроллером)

Всем огромное спасибо за помощь, особеннно Uriy!!!

Изменено пользователем adrvyho

Поделиться сообщением


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

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

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

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

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

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

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

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

×
×
  • Создать...