cancel
Showing results for 
Search instead for 
Did you mean: 

USB on H7: unable to open the port

Lagodolio
Senior

Hello!

I'm migrating from STM32F7 to H7 MCU, but I incurred a strange problem (well, two strange problems...).

I have a QT program that opens COM ports by:

void Sensor_interface::open_port()
{
  if (Device_Sensor_Port.isEmpty())
    {
      qDebug()<<"No Sensor port present-"<<Device_Sensor_Port;
    }
  else
  {
  qDebug()<<"DEVICE Port" << Device_Sensor_Port; // It prints "COM3"
  sensor_used_port.setPortName(Device_Sensor_Port);
  sensor_used_port.setBaudRate(BAUDRATE_SENSOR); 
  sensor_used_port.setDataBits (QSerialPort::Data8);
  sensor_used_port.setParity(QSerialPort::NoParity);
  sensor_used_port.setStopBits (QSerialPort::OneStop);
  sensor_used_port.setFlowControl (QSerialPort::NoFlowControl);
  sensor_used_port.open (QIODevice::ReadOnly);
  sensor_used_port.setDataTerminalReady(true);
  }
}
 

and this function is OK with my F7.

On H7, instead, the COM port is correctly recognized (as COM3) but the open command fails:

bool QSerialPort::setDataTerminalReady(bool): device not open

If I open that port with another program, (i.e. ARDUINO terminal) all works great and I can see STM32H7 messages.

The second strange thing is that USB works only with the SWD debugger connected.

I use an STM32F446RE as an SWD debugger/programmer (it is on COM4). If I remove the USB connected to STM32F446RE, the system stop sending messages.

My H7 is externally supplied.

I can send the code if it is useful...

Thanks,

Mario

2 REPLIES 2
Lagodolio
Senior

This is the freertos.c file:

/* USER CODE BEGIN Header */
/**
  ******************************************************************************
  * File Name          : freertos.c
  * Description        : Code for freertos applications
  ******************************************************************************
  * @attention
  *
  * <h2><center>&copy; Copyright (c) 2021 STMicroelectronics.
  * All rights reserved.</center></h2>
  *
  * This software component is licensed by ST under Ultimate Liberty license
  * SLA0044, the "License"; You may not use this file except in compliance with
  * the License. You may obtain a copy of the License at:
  *                             www.st.com/SLA0044
  *
  ******************************************************************************
  */
/* USER CODE END Header */
 
/* Includes ------------------------------------------------------------------*/
#include "FreeRTOS.h"
#include "task.h"
#include "main.h"
#include "cmsis_os.h"
 
/* USER CODE BEGIN Variables */
 
/* USER CODE END Variables */
/* Definitions for defaultTask */
osThreadId_t defaultTaskHandle;
const osThreadAttr_t defaultTask_attributes = {
  .name = "defaultTask",
  .priority = (osPriority_t) osPriorityNormal,
  .stack_size = 1920 * 4
};
/* Definitions for USB_DOUT */
osThreadId_t USB_DOUTHandle;
const osThreadAttr_t USB_DOUT_attributes = {
  .name = "USB_DOUT",
  .priority = (osPriority_t) osPriorityNormal1,
  .stack_size = 128 * 4
};
 
/* Private function prototypes -----------------------------------------------*/
/* USER CODE BEGIN FunctionPrototypes */
 
/* USER CODE END FunctionPrototypes */
 
void StartDefaultTask(void *argument);
void USB_Data_Out(void *argument);
 
extern void MX_USB_DEVICE_Init(void);
void MX_FREERTOS_Init(void); /* (MISRA C 2004 rule 8.1) */
 
/**
  * @brief  FreeRTOS initialization
  * @param  None
  * @retval None
  */
void MX_FREERTOS_Init(void) {
  
  /* Create the thread(s) */
  /* creation of defaultTask */
  defaultTaskHandle = osThreadNew(StartDefaultTask, NULL, &defaultTask_attributes);
 
  /* creation of USB_DOUT */
  USB_DOUTHandle = osThreadNew(USB_Data_Out, NULL, &USB_DOUT_attributes);
 
}
 
/* USER CODE BEGIN Header_StartDefaultTask */
/**
  * @brief  Function implementing the defaultTask thread.
  * @param  argument: Not used
  * @retval None
  */
/* USER CODE END Header_StartDefaultTask */
void StartDefaultTask(void *argument)
{
  /* init code for USB_DEVICE */
  MX_USB_DEVICE_Init();
  /* USER CODE BEGIN StartDefaultTask */
  /* Infinite loop */
  for(;;)
  {
    osDelay(1);
  }
  /* USER CODE END StartDefaultTask */
}
 
/* USER CODE BEGIN Header_USB_Data_Out */
/**
* @brief Function implementing the USB_DOUT thread.
* @param argument: Not used
* @retval None
*/
 
/* USER CODE END Header_USB_Data_Out */
void USB_Data_Out(void *argument)
{
  /* USER CODE BEGIN USB_Data_Out */
	MX_USB_DEVICE_Init();
  /* Infinite loop */
	uint8_t UserTxBuffer[] = "Hello World!!\n";
 
		for(;;)
	  {
		  CDC_Transmit_FS(UserTxBuffer, sizeof(UserTxBuffer)-1);
 
 
	    osDelay(1);
	  }
  /* USER CODE END USB_Data_Out */
}
 
/* Private application code --------------------------------------------------*/
/* USER CODE BEGIN Application */
 
/* USER CODE END Application */
 
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

Lagodolio
Senior

The USB CDC is implemented in usbd_cdc_if.c:

/* USER CODE BEGIN Header */
/**
  ******************************************************************************
  * @file           : usbd_cdc_if.c
  * @version        : v1.0_Cube
  * @brief          : Usb device for Virtual Com Port.
  ******************************************************************************
  * @attention
  *
  * <h2><center>&copy; Copyright (c) 2021 STMicroelectronics.
  * All rights reserved.</center></h2>
  *
  * This software component is licensed by ST under Ultimate Liberty license
  * SLA0044, the "License"; You may not use this file except in compliance with
  * the License. You may obtain a copy of the License at:
  *                             www.st.com/SLA0044
  *
  ******************************************************************************
  */
/* USER CODE END Header */
 
/* Includes ------------------------------------------------------------------*/
#include "usbd_cdc_if.h"
 
uint8_t UserRxBufferFS[APP_RX_DATA_SIZE];
/** Data to send over USB CDC are stored in this buffer   */
uint8_t UserTxBufferFS[APP_TX_DATA_SIZE];
 
/* USER CODE BEGIN PRIVATE_VARIABLES */
 
/* USER CODE END PRIVATE_VARIABLES */
 
/**
  * @}
  */
 
/** @defgroup USBD_CDC_IF_Exported_Variables USBD_CDC_IF_Exported_Variables
  * @brief Public variables.
  * @{
  */
 
extern USBD_HandleTypeDef hUsbDeviceFS;
 
/* USER CODE BEGIN EXPORTED_VARIABLES */
 
/* USER CODE END EXPORTED_VARIABLES */
 
/**
  * @}
  */
 
/** @defgroup USBD_CDC_IF_Private_FunctionPrototypes USBD_CDC_IF_Private_FunctionPrototypes
  * @brief Private functions declaration.
  * @{
  */
 
static int8_t CDC_Init_FS(void);
static int8_t CDC_DeInit_FS(void);
static int8_t CDC_Control_FS(uint8_t cmd, uint8_t* pbuf, uint16_t length);
static int8_t CDC_Receive_FS(uint8_t* pbuf, uint32_t *Len);
static int8_t CDC_TransmitCplt_FS(uint8_t *pbuf, uint32_t *Len, uint8_t epnum);
 
/* USER CODE BEGIN PRIVATE_FUNCTIONS_DECLARATION */
 
/* USER CODE END PRIVATE_FUNCTIONS_DECLARATION */
 
/**
  * @}
  */
 
USBD_CDC_ItfTypeDef USBD_Interface_fops_FS =
{
  CDC_Init_FS,
  CDC_DeInit_FS,
  CDC_Control_FS,
  CDC_Receive_FS,
  CDC_TransmitCplt_FS
};
 
/* Private functions ---------------------------------------------------------*/
/**
  * @brief  Initializes the CDC media low layer over the FS USB IP
  * @retval USBD_OK if all operations are OK else USBD_FAIL
  */
static int8_t CDC_Init_FS(void)
{
  /* USER CODE BEGIN 3 */
  /* Set Application Buffers */
  USBD_CDC_SetTxBuffer(&hUsbDeviceFS, UserTxBufferFS, 0);
  USBD_CDC_SetRxBuffer(&hUsbDeviceFS, UserRxBufferFS);
  return (USBD_OK);
  /* USER CODE END 3 */
}
 
/**
  * @brief  DeInitializes the CDC media low layer
  * @retval USBD_OK if all operations are OK else USBD_FAIL
  */
static int8_t CDC_DeInit_FS(void)
{
  /* USER CODE BEGIN 4 */
  return (USBD_OK);
  /* USER CODE END 4 */
}
 
/**
  * @brief  Manage the CDC class requests
  * @param  cmd: Command code
  * @param  pbuf: Buffer containing command data (request parameters)
  * @param  length: Number of data to be sent (in bytes)
  * @retval Result of the operation: USBD_OK if all operations are OK else USBD_FAIL
  */
static int8_t CDC_Control_FS(uint8_t cmd, uint8_t* pbuf, uint16_t length)
{
  /* USER CODE BEGIN 5 */
  switch(cmd)
  {
    case CDC_SEND_ENCAPSULATED_COMMAND:
 
    break;
 
    case CDC_GET_ENCAPSULATED_RESPONSE:
 
    break;
 
    case CDC_SET_COMM_FEATURE:
 
    break;
 
    case CDC_GET_COMM_FEATURE:
 
    break;
 
    case CDC_CLEAR_COMM_FEATURE:
 
    break;
 
  /*******************************************************************************/
  /* Line Coding Structure                                                       */
  /*-----------------------------------------------------------------------------*/
  /* Offset | Field       | Size | Value  | Description                          */
  /* 0      | dwDTERate   |   4  | Number |Data terminal rate, in bits per second*/
  /* 4      | bCharFormat |   1  | Number | Stop bits                            */
  /*                                        0 - 1 Stop bit                       */
  /*                                        1 - 1.5 Stop bits                    */
  /*                                        2 - 2 Stop bits                      */
  /* 5      | bParityType |  1   | Number | Parity                               */
  /*                                        0 - None                             */
  /*                                        1 - Odd                              */
  /*                                        2 - Even                             */
  /*                                        3 - Mark                             */
  /*                                        4 - Space                            */
  /* 6      | bDataBits  |   1   | Number Data bits (5, 6, 7, 8 or 16).          */
  /*******************************************************************************/
    case CDC_SET_LINE_CODING:
 
    break;
 
    case CDC_GET_LINE_CODING:
 
    break;
 
    case CDC_SET_CONTROL_LINE_STATE:
 
    break;
 
    case CDC_SEND_BREAK:
 
    break;
 
  default:
    break;
  }
 
  return (USBD_OK);
  /* USER CODE END 5 */
}
 
/**
  * @brief  Data received over USB OUT endpoint are sent over CDC interface
  *         through this function.
  *
  *         @note
  *         This function will issue a NAK packet on any OUT packet received on
  *         USB endpoint until exiting this function. If you exit this function
  *         before transfer is complete on CDC interface (ie. using DMA controller)
  *         it will result in receiving more data while previous ones are still
  *         not sent.
  *
  * @param  Buf: Buffer of data to be received
  * @param  Len: Number of data received (in bytes)
  * @retval Result of the operation: USBD_OK if all operations are OK else USBD_FAIL
  */
static int8_t CDC_Receive_FS(uint8_t* Buf, uint32_t *Len)
{
  /* USER CODE BEGIN 6 */
  USBD_CDC_SetRxBuffer(&hUsbDeviceFS, &Buf[0]);
  USBD_CDC_ReceivePacket(&hUsbDeviceFS);
  return (USBD_OK);
  /* USER CODE END 6 */
}
 
/**
  * @brief  CDC_Transmit_FS
  *         Data to send over USB IN endpoint are sent over CDC interface
  *         through this function.
  *         @note
  *
  *
  * @param  Buf: Buffer of data to be sent
  * @param  Len: Number of data to be sent (in bytes)
  * @retval USBD_OK if all operations are OK else USBD_FAIL or USBD_BUSY
  */
uint8_t CDC_Transmit_FS(uint8_t* Buf, uint16_t Len)
{
  uint8_t result = USBD_OK;
  /* USER CODE BEGIN 7 */
  USBD_CDC_HandleTypeDef *hcdc = (USBD_CDC_HandleTypeDef*)hUsbDeviceFS.pClassData;
  if (hcdc->TxState != 0){
    return USBD_BUSY;
  }
  USBD_CDC_SetTxBuffer(&hUsbDeviceFS, Buf, Len);
  result = USBD_CDC_TransmitPacket(&hUsbDeviceFS);
  /* USER CODE END 7 */
  return result;
}
 
/**
  * @brief  CDC_TransmitCplt_FS
  *         Data transmited callback
  *
  *         @note
  *         This function is IN transfer complete callback used to inform user that
  *         the submitted Data is successfully sent over USB.
  *
  * @param  Buf: Buffer of data to be received
  * @param  Len: Number of data received (in bytes)
  * @retval Result of the operation: USBD_OK if all operations are OK else USBD_FAIL
  */
static int8_t CDC_TransmitCplt_FS(uint8_t *Buf, uint32_t *Len, uint8_t epnum)
{
  uint8_t result = USBD_OK;
  /* USER CODE BEGIN 13 */
  UNUSED(Buf);
  UNUSED(Len);
  UNUSED(epnum);
  /* USER CODE END 13 */
  return result;
}
 
/* USER CODE BEGIN PRIVATE_FUNCTIONS_IMPLEMENTATION */
 
/* USER CODE END PRIVATE_FUNCTIONS_IMPLEMENTATION */
 
/**
  * @}
  */
 
/**
  * @}
  */
 
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/