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

查看: 3396|回复: 21

[STM32L476] [NUCLEO-L476RG开发] 先写段CPP玩玩,重载<<运算符

[复制链接]

9

主题

646

回帖

24

蝴蝶豆

论坛元老

最后登录
2020-9-4
发表于 2015-10-26 11:07:10 | 显示全部楼层 |阅读模式
看上去工作的挺好!
OStream & operator<<(OStream& stream,char c)
{
        stream.Putc(c);
        return stream;
}
//;OStream 基类名.

O0 下编译
; operator<<(OStream &, char)
EXPORT _ZlsR7OStreamc
_ZlsR7OStreamc
PUSH            {R4-R6,LR}
MOV             R4, R0  
MOV             R5, R1  
LDR             R0, [R4]  
MOV             R1, R5
LDR             R2, [R0]
MOV             R0, R4
BLX             R2
MOV             R0, R4
POP             {R4-R6,PC}
O3 下编译
; operator<<(OStream &, char)
EXPORT _ZlsR7OStreamc
_ZlsR7OStreamc
PUSH            {R4,LR}
MOV             R4, R0
LDR             R0, [R0]
LDR             R2, [R0]
MOV             R0, R4
BLX             R2
MOV             R0, R4
POP             {R4,PC}
=====================================

LDR             R2, [R0]  
BLX             R2
是获取成员函数地址(这具体与调用那个函数有关),并跳转。
R0,R1什么传个参数就不讲了
可以看出优化明显把
MOV             R5, R1;  MOV             R1, R5;
给优化了。

另外,如预计的那样:main在返回之前调用了析构函数
。。。。
BL              _ZlsR7OStreamPc ; operator<<(OStream &,char *)
ADD             R0, SP, #0x170+var_90
BL              _ZN11UartOStreamD2Ev ; UartOStream::~UartOStream()
MOVS            R0, #1
ADD             SP, SP, #0x154
POP.W           {R4-R9,PC}
; End of function main

感觉好水。。。

代码:

myio.cpp:

  1. #include "myio.hpp"
  2. OStream & operator<<(OStream& stream,char c)
  3. {
  4.         stream.Putc(c);
  5.         return stream;
  6. }

  7. OStream & operator<<(OStream& stream,char* s)
  8. {
  9.         stream.Puts(s);
  10.         return stream;
  11. }


  12. UartOStream uartout;

  13. LedOStream   led;
复制代码
myio.hpp
  1. #ifndef _MY_IO_HPP
  2. #define _MY_IO_HPP
  3. #include "stm32l4xx_hal.h"

  4. class OStream
  5. {
  6. public:
  7.         OStream()
  8.         {
  9.         }
  10.         virtual void Putc(char c) = 0;
  11.         virtual void Puts(char* s) = 0;
  12. };

  13. class UartOStream: public OStream
  14. {
  15. private:
  16.         UART_HandleTypeDef UARTHandle;
  17. public:
  18.         UartOStream()
  19.         {
  20.           UARTHandle.Instance = USART2;
  21.                 UARTHandle.Init.BaudRate = 9600;
  22.                 UARTHandle.Init.WordLength = UART_WORDLENGTH_8B;
  23.                 UARTHandle.Init.StopBits = UART_STOPBITS_1;
  24.                 UARTHandle.Init.Parity = UART_PARITY_NONE;
  25.                 UARTHandle.Init.HwFlowCtl  = UART_HWCONTROL_NONE;
  26.                 UARTHandle.Init.Mode = UART_MODE_TX_RX;
  27.                 UARTHandle.Init.OverSampling = UART_OVERSAMPLING_16;
  28.                 UARTHandle.Init.OneBitSampling = UART_ONE_BIT_SAMPLE_DISABLE;
  29.                
  30.                 GPIO_InitTypeDef  GPIO_InitStruct;
  31.     /* Enable UART2 GPIO TX/RX clock */
  32.     __HAL_RCC_GPIOA_CLK_ENABLE();
  33.     /* Enable USART2 clock */
  34.     __HAL_RCC_USART2_CLK_ENABLE();   
  35.     /* Configure USART2 Rx and Tx as alternate function  */
  36.     GPIO_InitStruct.Pin = GPIO_PIN_2 | GPIO_PIN_3;
  37.     GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
  38.     GPIO_InitStruct.Pull = GPIO_PULLUP;
  39.     GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_MEDIUM; // GPIO_SPEED_FREQ_VERY_HIGH;
  40.     GPIO_InitStruct.Alternate = GPIO_AF7_USART2;
  41.     HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);
  42.    
  43.     /* Enable and set USART2 Interrupt to the highest priority */
  44.     HAL_NVIC_SetPriority(USART2_IRQn, 1, 0);
  45.     HAL_NVIC_EnableIRQ(USART2_IRQn);
  46.                
  47.                 if(HAL_UART_Init(&UARTHandle) != HAL_OK)
  48.                 {
  49.                         //throw;
  50.                         while(1);
  51.                 }
  52.         }
  53.         virtual void Putc(char c)
  54.         {
  55.                 HAL_UART_Transmit(&UARTHandle, (uint8_t *)&c, 1, 0xFFFF);
  56.         }
  57.         virtual void Puts(char *s)
  58.         {
  59.                 while(*s)
  60.                 {
  61.                         Putc(*(s++));
  62.                 }
  63.         }
  64.         ~UartOStream()
  65.         {
  66.                 char ADDR[18];
  67.                 sprintf(ADDR,"0x%08x\n",this);
  68.                 Puts("I AM BEING KILLED , I AM AT ");
  69.                 Puts(ADDR);
  70.         }
  71. };

  72. class LedOStream :public OStream
  73. {
  74. private:
  75.         int m_Interval;
  76. public:
  77.         void SetInterval(int n){m_Interval = n;}
  78.         ~LedOStream()
  79.         {
  80.                 HAL_GPIO_WritePin(GPIOA,GPIO_PIN_5,GPIO_PIN_RESET);
  81.         }
  82.         LedOStream()
  83.         {
  84.           m_Interval = 0;
  85.                
  86.                 GPIO_InitTypeDef  gpioinitstruct;
  87.                 __HAL_RCC_GPIOA_CLK_ENABLE();
  88.                 /* Configure the GPIO_LED pin */
  89.                 gpioinitstruct.Pin   = GPIO_PIN_5;
  90.                 gpioinitstruct.Mode  = GPIO_MODE_OUTPUT_PP;
  91.                 gpioinitstruct.Pull  = GPIO_NOPULL;
  92.                 gpioinitstruct.Speed = GPIO_SPEED_FREQ_HIGH;
  93.                 HAL_GPIO_Init(GPIOA, &gpioinitstruct);
  94.                 HAL_GPIO_WritePin(GPIOA,GPIO_PIN_5,GPIO_PIN_SET);
  95.         }
  96.         virtual void Putc(char c)
  97.         {
  98.                         if(c=='1')
  99.                                 HAL_GPIO_WritePin(GPIOA,GPIO_PIN_5,GPIO_PIN_SET);
  100.                         else if(c=='0')
  101.                                 HAL_GPIO_WritePin(GPIOA,GPIO_PIN_5,GPIO_PIN_RESET);
  102.                                 
  103.         }
  104.         virtual void Puts(char *s)
  105.         {
  106.                 while(*s)
  107.                 {
  108.                         Putc(*(s++));
  109.                         int t = m_Interval;
  110.                         while(t--);
  111.                 }
  112.         }
  113.         
  114. };
  115. OStream &  operator<<(OStream& stream,char c);
  116. OStream &  operator<<(OStream& stream,char*s);


  117. extern UartOStream uartout;
  118. extern LedOStream   led;
  119. #endif
复制代码
main.cpp
  1. #include "myio.hpp"
  2. #include "stm32l4xx_hal.h"

  3.         char ADDR1[18];
  4.         char ADDR2[18];
  5.         char ADDR3[18];
  6.         char ADDR4[18];
  7. static UartOStream uartouttest4;
  8. int main(void)
  9. {
  10.         UartOStream uartouttest2;
  11.         UartOStream *uartouttest3 = new(UartOStream);
  12.         HAL_Init();
  13.         

  14.         sprintf(ADDR1,"0x%08x",&uartout);
  15.         sprintf(ADDR2,"0x%08x",&uartouttest2);
  16.         sprintf(ADDR3,"0x%08x",uartouttest3);
  17.         sprintf(ADDR4,"0x%08x",uartouttest4);
  18.         
  19.         uartout << "uartout" << "ADDR = " << ADDR1 <<'\r' <<'\n';
  20.         uartouttest2 << "uartouttest2" << "ADDR = " << ADDR2 << "\r\n";
  21.         *uartouttest3 << "uartouttest3" << "ADDR = " << ADDR3 << "\r\n";
  22.         uartouttest4 << "uartouttest4" << "ADDR = " << ADDR4 << "\r\n";
  23.         
  24.         led.SetInterval(200000);
  25.         led<<"101010101010101010101";
  26.         //while(1);
  27.         return 1;
  28. }

复制代码


评分

参与人数 1ST金币 +20 收起 理由
沐紫 + 20

查看全部评分

<
回复

使用道具 举报

9

主题

646

回帖

24

蝴蝶豆

论坛元老

最后登录
2020-9-4
 楼主| 发表于 2015-10-26 11:09:14 | 显示全部楼层
初始化放在构造函数里是不对的!
回复 支持 反对

使用道具 举报

47

主题

1636

回帖

7

蝴蝶豆

论坛元老

最后登录
2020-10-28
发表于 2015-10-26 11:40:48 | 显示全部楼层
能用OOP,不错。
优化的话,关键你用的编译器是哪个?
回复 支持 反对

使用道具 举报

10

主题

1651

回帖

0

蝴蝶豆

论坛元老

最后登录
2020-2-15
发表于 2015-10-26 12:09:18 | 显示全部楼层
搞单片机玩C++的肯定是高手。
回复 支持 反对

使用道具 举报

9

主题

646

回帖

24

蝴蝶豆

论坛元老

最后登录
2020-9-4
 楼主| 发表于 2015-10-26 12:21:19 | 显示全部楼层
yanhaijian 发表于 2015-10-26 12:09
搞单片机玩C++的肯定是高手。

C++是大一必修课
回复 支持 反对

使用道具 举报

4

主题

101

回帖

0

蝴蝶豆

初级会员

最后登录
2016-7-26
发表于 2015-10-26 12:25:58 | 显示全部楼层
不错哈
回复 支持 反对

使用道具 举报

10

主题

1651

回帖

0

蝴蝶豆

论坛元老

最后登录
2020-2-15
发表于 2015-10-26 12:29:36 | 显示全部楼层

单片机开发一般只用C,很少有人去研究C++。
回复 支持 反对

使用道具 举报

9

主题

646

回帖

24

蝴蝶豆

论坛元老

最后登录
2020-9-4
 楼主| 发表于 2015-10-26 13:09:22 | 显示全部楼层
yanhaijian 发表于 2015-10-26 12:29
单片机开发一般只用C,很少有人去研究C++。

嗯,是的
回复 支持 反对

使用道具 举报

57

主题

1159

回帖

0

蝴蝶豆

金牌会员

最后登录
2020-12-6
发表于 2015-10-26 15:22:03 | 显示全部楼层
帮顶                     
回复 支持 反对

使用道具 举报

57

主题

1159

回帖

0

蝴蝶豆

金牌会员

最后登录
2020-12-6
发表于 2015-10-26 15:22:25 | 显示全部楼层
帮顶                        
回复 支持 反对

使用道具 举报

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