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

查看: 3393|回复: 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管理
行使您的权利
官方最新发布
STM32Cube扩展软件包
意法半导体边缘AI套件
ST - 理想汽车豪华SUV案例
ST意法半导体智能家居案例
STM32 ARM Cortex 32位微控制器
关注我们
st-img 微信公众号
st-img 手机版