你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

关于F4的 USB虚拟串口

[复制链接]
JQChirs 提问时间:2018-9-19 11:25 /
在F407上调试成功的虚拟串口程序,在F446上跑不起来!问题就是不能识别驱动,446上面D+上面都没有高电平出现(F4内部是集成1.5K上拉电阻的)。
我使用的是标准外设库,USB外设库是USB_HOST-Device_LibV2.1和V2.2。很多网友说用CubeMX一配置就配置出来,是的没错,我也试了。证明了我的硬件是OK的!
但是我已经用标准外设库把整个工程写了百分之九十,如果就是因为虚拟串口驱动装不上去,换成HAL库那就太耽误项目进度了!
贴代码分析原因吧。
如下为主函数。
  1. USB_OTG_CORE_HANDLE  USB_OTG_dev;

  2. int main(void)
  3. {
  4.   SystemInit();

  5.   USBD_Init(&USB_OTG_dev,
  6.             USB_OTG_FS_CORE_ID,
  7.             &USR_desc,
  8.             &USBD_CDC_cb,
  9.             &USR_cb);
  10.   
  11.   while(1)
  12.   {
  13.    
  14.   }

  15. }
复制代码
       宏是这么定义的!        STM32F40_41xxx
        USE_USB_OTG_FS  如果要换成F446的话直接改成STM32F446xx。
        对于两个不同的宏,预编译就只能在SystemInit();里面了。
        先看时钟配置吧!

  1. #if defined(STM32F40_41xxx) || defined(STM32F427_437xx) || defined(STM32F429_439xx) || defined(STM32F469_479xx)
  2. /* #define DATA_IN_ExtSRAM */
  3. #endif /* STM32F40_41xxx || STM32F427_437x || STM32F429_439xx || STM32F469_479xx */

  4. #if defined(STM32F427_437xx) || defined(STM32F429_439xx) || defined(STM32F446xx) || defined(STM32F469_479xx)
  5. /* #define DATA_IN_ExtSDRAM */
  6. #endif /* STM32F427_437x || STM32F429_439xx || STM32F446xx || STM32F469_479xx */

  7. #if defined(STM32F410xx) || defined(STM32F411xE)
  8. /*!< Uncomment the following line if you need to clock the STM32F410xx/STM32F411xE by HSE Bypass
  9.      through STLINK MCO pin of STM32F103 microcontroller. The frequency cannot be changed
  10.      and is fixed at 8 MHz.
  11.      Hardware configuration needed for Nucleo Board:
  12.      ?SB54, SB55 OFF
  13.      ?R35 removed
  14.      ?SB16, SB50 ON */
  15. /* #define USE_HSE_BYPASS */

  16. #if defined(USE_HSE_BYPASS)     
  17. #define HSE_BYPASS_INPUT_FREQUENCY   8000000
  18. #endif /* USE_HSE_BYPASS */   
  19. #endif /* STM32F410xx || STM32F411xE */
  20.    
  21. /*!< Uncomment the following line if you need to relocate your vector Table in
  22.      Internal SRAM. */
  23. /* #define VECT_TAB_SRAM */
  24. #define VECT_TAB_OFFSET  0x00 /*!< Vector Table base offset field.
  25.                                    This value must be a multiple of 0x200. */
  26. /******************************************************************************/

  27. /************************* PLL Parameters *************************************/
  28. #if defined(STM32F40_41xxx) || defined(STM32F427_437xx) || defined(STM32F429_439xx) || defined(STM32F401xx) || defined(STM32F469_479xx)
  29. /* PLL_VCO = (HSE_VALUE or HSI_VALUE / PLL_M) * PLL_N */
  30. #define PLL_M      8
  31. #elif defined(STM32F412xG) || defined (STM32F446xx)
  32. #define PLL_M      8
  33. #elif defined (STM32F410xx) || defined (STM32F411xE)
  34. #if defined(USE_HSE_BYPASS)
  35.   #define PLL_M      8   
  36. #else /* !USE_HSE_BYPASS */
  37.   #define PLL_M      8
  38. #endif /* USE_HSE_BYPASS */
  39. #else
  40. #endif /* STM32F40_41xxx || STM32F427_437xx || STM32F429_439xx || STM32F401xx || STM32F469_479xx */  

  41. /* USB OTG FS, SDIO and RNG Clock =  PLL_VCO / PLLQ */
  42. #define PLL_Q      7

  43. #if defined(STM32F446xx)
  44. /* PLL division factor for I2S, SAI, SYSTEM and SPDIF: Clock =  PLL_VCO / PLLR */
  45. #define PLL_R      7
  46. #elif defined(STM32F412xG)
  47. #define PLL_R      2
  48. #else
  49. #endif /* STM32F446xx */

  50. #if defined(STM32F427_437xx) || defined(STM32F429_439xx) || defined(STM32F446xx) || defined(STM32F469_479xx)
  51. #define PLL_N 336
  52. //#define PLL_N 360
  53. /* SYSCLK = PLL_VCO / PLL_P */
  54. #define PLL_P      2
  55. #endif /* STM32F427_437x || STM32F429_439xx || STM32F446xx || STM32F469_479xx */

  56. #if defined (STM32F40_41xxx)
  57. #define PLL_N  336
  58. /* SYSCLK = PLL_VCO / PLL_P */
  59. #define PLL_P      2
  60. #endif /* STM32F40_41xxx */

  61. #if defined(STM32F401xx)
  62. #define PLL_N      336
  63. /* SYSCLK = PLL_VCO / PLL_P */
  64. #define PLL_P      4
  65. #endif /* STM32F401xx */

  66. #if defined(STM32F410xx) || defined(STM32F411xE) || defined(STM32F412xG)
  67. #define PLL_N      400
  68. /* SYSCLK = PLL_VCO / PLL_P */
  69. #define PLL_P      4   
  70. #endif /* STM32F410xx || STM32F411xE */

  71. /******************************************************************************/
复制代码
再看SystemInit();函数
  1.   /* FPU settings ------------------------------------------------------------*/
  2.   #if (__FPU_PRESENT == 1) && (__FPU_USED == 1)
  3.     SCB->CPACR |= ((3UL << 10*2)|(3UL << 11*2));  /* set CP10 and CP11 Full Access */
  4.   #endif
  5.   /* Reset the RCC clock configuration to the default reset state ------------*/
  6.   /* Set HSION bit */
  7.   RCC->CR |= (uint32_t)0x00000001;

  8.   /* Reset CFGR register */
  9.   RCC->CFGR = 0x00000000;

  10.   /* Reset HSEON, CSSON and PLLON bits */
  11.   RCC->CR &= (uint32_t)0xFEF6FFFF;

  12.   /* Reset PLLCFGR register */
  13.   RCC->PLLCFGR = 0x24003010;

  14.   /* Reset HSEBYP bit */
  15.   RCC->CR &= (uint32_t)0xFFFBFFFF;

  16.   /* Disable all interrupts */
  17.   RCC->CIR = 0x00000000;

  18. #if defined(DATA_IN_ExtSRAM) || defined(DATA_IN_ExtSDRAM)
  19.   SystemInit_ExtMemCtl();
  20. #endif /* DATA_IN_ExtSRAM || DATA_IN_ExtSDRAM */
  21.          
  22.   /* Configure the System clock source, PLL Multiplier and Divider factors,
  23.      AHB/APBx prescalers and Flash settings ----------------------------------*/
  24.   SetSysClock();

  25.   /* Configure the Vector Table location add offset address ------------------*/
  26. #ifdef VECT_TAB_SRAM
  27.   SCB->VTOR = SRAM_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal SRAM */
  28. #else
  29.   SCB->VTOR = FLASH_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal FLASH */
  30. #endif
  31. }
复制代码
    再看SetSysClock();
  1. static void SetSysClock(void)
  2. {
  3. /******************************************************************************/
  4. /*            PLL (clocked by HSE) used as System clock source                */
  5. /******************************************************************************/
  6.   __IO uint32_t StartUpCounter = 0, HSEStatus = 0;
  7.   
  8.   /* Enable HSE */
  9.   RCC->CR |= ((uint32_t)RCC_CR_HSEON);

  10.   /* Wait till HSE is ready and if Time out is reached exit */
  11.   do
  12.   {
  13.     HSEStatus = RCC->CR & RCC_CR_HSERDY;
  14.     StartUpCounter++;
  15.   } while((HSEStatus == 0) && (StartUpCounter != HSE_STARTUP_TIMEOUT));

  16.   if ((RCC->CR & RCC_CR_HSERDY) != RESET)
  17.   {
  18.     HSEStatus = (uint32_t)0x01;
  19.   }
  20.   else
  21.   {
  22.     HSEStatus = (uint32_t)0x00;
  23.   }

  24.   if (HSEStatus == (uint32_t)0x01)
  25.   {
  26.     /* Select regulator voltage output Scale 1 mode */
  27.     RCC->APB1ENR |= RCC_APB1ENR_PWREN;
  28.     PWR->CR |= PWR_CR_VOS;

  29.     /* HCLK = SYSCLK / 1*/
  30.     RCC->CFGR |= RCC_CFGR_HPRE_DIV1;
  31.    
  32.     /* PCLK2 = HCLK / 2*/
  33.     RCC->CFGR |= RCC_CFGR_PPRE2_DIV2;   
  34.    
  35.     /* PCLK1 = HCLK / 4*/
  36.     RCC->CFGR |= RCC_CFGR_PPRE1_DIV4;     //到这里没有区别


  37. #if defined(STM32F40_41xxx) || defined(STM32F427_437xx) || defined(STM32F429_439xx) || defined(STM32F401xx) || defined(STM32F469_479xx)   
  38.     /* Configure the main PLL */
  39.     RCC->PLLCFGR = PLL_M | (PLL_N << 6) | (((PLL_P >> 1) -1) << 16) |
  40.                    (RCC_PLLCFGR_PLLSRC_HSE) | (PLL_Q << 24);
  41. #endif /* STM32F40_41xxx || STM32F401xx || STM32F427_437x || STM32F429_439xx || STM32F469_479xx */

  42. #if  defined(STM32F412xG) || defined(STM32F446xx)
  43.     /* Configure the main PLL */
  44.     RCC->PLLCFGR = PLL_M | (PLL_N << 6) | (((PLL_P >> 1) -1) << 16) |
  45.                    (RCC_PLLCFGR_PLLSRC_HSE) | (PLL_Q << 24) | (PLL_R << 28);  //这里不过是PLL_R给I2S使用
  46.    
  47. #endif /* STM32F412xG || STM32F446xx */   
  48.    
  49.     /* Enable the main PLL */
  50.     RCC->CR |= RCC_CR_PLLON; //把主PLL开启,那么给USB的第二个PLL的相关配置在哪
  51.     //答:主PLL出来时钟之后,直接去配置Q就出来给USB_OTG_FS使用,并不存在开启第二个PLL。
  52.     /* Wait till the main PLL is ready */
  53.     while((RCC->CR & RCC_CR_PLLRDY) == 0)
  54.     {
  55.     }
  56.    
  57. #if defined(STM32F427_437xx) || defined(STM32F429_439xx) || defined(STM32F446xx) || defined(STM32F469_479xx)
  58.     /* Enable the Over-drive to extend the clock frequency to 180 Mhz */
  59.     PWR->CR |= PWR_CR_ODEN;
  60.     while((PWR->CSR & PWR_CSR_ODRDY) == 0)
  61.     {
  62.     }
  63.     PWR->CR |= PWR_CR_ODSWEN;
  64.     while((PWR->CSR & PWR_CSR_ODSWRDY) == 0)
  65.     {
  66.     }                                           //这里只是针对了电源
  67.     /* Configure Flash prefetch, Instruction cache, Data cache and wait state */
  68.     FLASH->ACR = FLASH_ACR_PRFTEN | FLASH_ACR_ICEN |FLASH_ACR_DCEN |FLASH_ACR_LATENCY_5WS;
  69. #endif /* STM32F427_437x || STM32F429_439xx || STM32F446xx || STM32F469_479xx */

  70. #if defined(STM32F40_41xxx)  || defined(STM32F412xG)   
  71.     /* Configure Flash prefetch, Instruction cache, Data cache and wait state */
  72.     FLASH->ACR = FLASH_ACR_PRFTEN | FLASH_ACR_ICEN |FLASH_ACR_DCEN |FLASH_ACR_LATENCY_5WS;
  73. #endif /* STM32F40_41xxx  || STM32F412xG */

  74.     /* Select the main PLL as system clock source */
  75.     RCC->CFGR &= (uint32_t)((uint32_t)~(RCC_CFGR_SW));
  76.     RCC->CFGR |= RCC_CFGR_SW_PLL;

  77.     /* Wait till the main PLL is used as system clock source */
  78.     while ((RCC->CFGR & (uint32_t)RCC_CFGR_SWS ) != RCC_CFGR_SWS_PLL);
  79.     {
  80.     }
  81.   }
  82.   else
  83.   { /* If HSE fails to start-up, the application will have wrong clock
  84.          configuration. User can add here some code to deal with this error */
  85.   }
  86.   
  87. /* STM32F40_41xxx || STM32F427_437xx || STM32F429_
复制代码



收藏 评论4 发布时间:2018-9-19 11:25

举报

4个回答
JQChirs 回答时间:2018-9-19 11:31:26
       我现在也只能怀疑是时钟的问题了!因为对于同样是F4的单片机来说,相关OTG_FS无论是引脚配置,时钟,中断向量表还是寄存器肯定是相同的!
       我甚至打印对照相关OTG_FS的寄存器发现并没有什么大的区别。
      
馒头弟 回答时间:2018-9-20 09:12:36
时钟没啥问题诶,你用的高速还是全速
RCC.png

评分

参与人数 1蝴蝶豆 +3 收起 理由
zero99 + 3

查看全部评分

wenyangzeng 回答时间:2018-9-20 09:53:53
F407的主频是168MHZ,F446主频是180MHZ.楼主要检查一下F446系统时钟分频后的USB时钟频率是否正确。

评分

参与人数 1蝴蝶豆 +2 收起 理由
zero99 + 2

查看全部评分

shenxiaolin_mai 回答时间:2018-9-20 13:33:40
过来学习学习

评分

参与人数 1ST金币 -1 收起 理由
zero99 -1 求助帖不要灌水啊

查看全部评分

所属标签

相似问题

官网相关资源

关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
STM32N6 AI生态系统
STM32MCU,MPU高性能GUI
ST ACEPACK电源模块
意法半导体生物传感器
STM32Cube扩展软件包
关注我们
st-img 微信公众号
st-img 手机版