[STM8] 关于IO口宏定义

[复制链接]
 楼主| XIZIRUI 发表于 2014-4-20 21:55 | 显示全部楼层 |阅读模式
本帖最后由 XIZIRUI 于 2014-4-23 21:48 编辑

为了便于程序移植,本人想把ST的IO像51一样的位定义进行宏定义,试了好久都木有实现,求教大虾,望解答的时候能给出一段完整的源代码,谢鸟

前两天发这个帖子的时候,写的不清楚,现在重新编辑一下。我用的是STM8,想可以像51一样 sbit LED=P1^1,大虾们,求指导中
mmuuss586 发表于 2014-4-20 21:57 | 显示全部楼层

比如PA.0=0?
yuanpooo 发表于 2014-4-21 09:30 | 显示全部楼层
本帖最后由 yuanpooo 于 2014-4-21 09:38 编辑

可以使用BitBanding,STM32F103系列可以参考正点原子的源码,他的论坛有开放,F4的可以看下我的这个(其实我也是参考正点原子的),在STM32F4Discovery验证通过

  1. // Header        :
  2. // File Name:bit_banding.h
  3. // Author        :---
  4. // Date                :2014/04/04
  5. // Explain        :        
  6. #ifndef __BIT_BANDING_H__
  7. #define __BIT_BANDING_H__


  8. //M4内核的GPIO寄存器基地址等
  9. #if defined (STM32F40_41xxx) || defined (STM32F427_437xx) || defined (STM32F429_439xx) || defined (STM32F401xx) || defined (STM32F40XX) || defined (STM32F427X)
  10. //这些宏定义在使用最新库函数时,都会有定义

  11. #include "stm32f4xx.h"

  12. #define GPIO_REG_ADDR_BASE                0x40020000ul
  13. #define GPIO_REG_ADDR_OFFSET        0x400ul

  14. #define GPIO_ODR_OFFSET                        0x14ul
  15. #define GPIO_IDR_OFFSET                        0x10ul

  16. #endif

  17. //M3内核的GPIO寄存器基地址
  18. #if defined (STM32F10X_LD) || defined (STM32F10X_LD_VL) || defined (STM32F10X_MD) || defined (STM32F10X_MD_VL) || defined (STM32F10X_HD) || defined (STM32F10X_HD_VL) || defined (STM32F10X_XL) || defined (STM32F10X_CL)

  19. #include "stm32f10x.h"

  20. #define GPIO_REG_ADDR_BASE                0x40010800ul
  21. #define GPIO_REG_ADDR_OFFSET        0x400ul

  22. #define GPIO_ODR_OFFSET                        0x0Cul
  23. #define GPIO_IDR_OFFSET                        0x08ul

  24. #endif


  25. //别名区的基地址的末地址,在M3和M4中是一样的,位地址的计算公式也是一样的

  26. //外设别名区的基地址
  27. #define BIT_BAND_ALIAS_PERIPHERAL_BASE        0x42000000ul

  28. #define BIT_BAND_ALIAS_PERIPHERAL_END        0x43FFFFFFul

  29. //SRAM别名区基地址
  30. #define BIT_BAND_ALIAS_SRAM_BASE                0x22000000ul
  31. //
  32. #define BIT_BAND_ALIAS_SRAM_END                        0x23FFFFFFul


  33. //在bitband区中 位地址的计算公式
  34. #define BIT_WORD_ADDR(ByteAddr, BitNumber)        ((ByteAddr&0xF0000000) + 0x2000000 + (ByteAddr&0x000FFFFF)*32 + (BitNumber&0x0000000F)*4)


  35. //将地址转换成指针,这样才能读写地址中的值
  36. #define CONVERT_TO_PTR(BitWordAddr)                ( *( (volatile unsigned long *)BitWordAddr ) )

  37. //BitNumber<16
  38. //输出
  39. #define PAout(BitNumber)        CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOA_BASE + GPIO_ODR_OFFSET, BitNumber) )
  40. #define PBout(BitNumber)        CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOB_BASE + GPIO_ODR_OFFSET, BitNumber) )
  41. #define PCout(BitNumber)        CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOC_BASE + GPIO_ODR_OFFSET, BitNumber) )
  42. #define PDout(BitNumber)        CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOD_BASE + GPIO_ODR_OFFSET, BitNumber) )
  43. #define PEout(BitNumber)        CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOE_BASE + GPIO_ODR_OFFSET, BitNumber) )
  44. #define PFout(BitNumber)        CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOF_BASE + GPIO_ODR_OFFSET, BitNumber) )
  45. #define PGout(BitNumber)        CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOG_BASE + GPIO_ODR_OFFSET, BitNumber) )
  46. #define PHout(BitNumber)        CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOH_BASE + GPIO_ODR_OFFSET, BitNumber) )
  47. //读输入
  48. #define PAin(BitNumber)                CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOA_BASE + GPIO_IDR_OFFSET, BitNumber) )
  49. #define PBin(BitNumber)                CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOB_BASE + GPIO_IDR_OFFSET, BitNumber) )
  50. #define PCin(BitNumber)                CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOC_BASE + GPIO_IDR_OFFSET, BitNumber) )
  51. #define PDin(BitNumber)                CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOD_BASE + GPIO_IDR_OFFSET, BitNumber) )
  52. #define PEin(BitNumber)                CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOE_BASE + GPIO_IDR_OFFSET, BitNumber) )
  53. #define PFin(BitNumber)                CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOF_BASE + GPIO_IDR_OFFSET, BitNumber) )
  54. #define PGin(BitNumber)                CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOG_BASE + GPIO_IDR_OFFSET, BitNumber) )
  55. #define PHin(BitNumber)                CONVERT_TO_PTR( BIT_WORD_ADDR(GPIOH_BASE + GPIO_IDR_OFFSET, BitNumber) )

  56. #endif

yhs0717 发表于 2014-8-12 15:36 | 显示全部楼层
yuanpooo 发表于 2014-4-21 09:30
可以使用BitBanding,STM32F103系列可以参考正点原子的源码,他的论坛有开放,F4的可以看下我的这个(其实我 ...

怎么样像你这样插入源代码
无为之益 发表于 2014-8-12 16:33 | 显示全部楼层
#define  LEDPin       (1<<2)     //假设PA2
#define  LED_ON      PA_ODR &= ~LEDPin     
#define  LED_OFF    PA_ODR |= LEDPin

当然,到底是电平为低时灯亮还是为高时灯亮,看你具体项目原理图设计,然后修改相应宏定义
hopewise 发表于 2014-8-12 16:58 | 显示全部楼层
位要用_Bool的,而不是C51的sbit.
_Bool RELAY     @PD_ODR:6;   //继电器输出控制脚

/*************变量定义*************/
typedef unsigned char uchar;
typedef unsigned int  uint;
_Bool   f_buzon=0;       //蜂鸣器响的标志位
myxiaonia 发表于 2014-8-12 22:45 | 显示全部楼层
轻易的使用外设寄存器位带常常带来巨大的隐患,原子的资料不错,st官方例程更不错,但是那些很多时候仅仅是demo而已,你得自己分辨
外设寄存器可能会被外设修改某些位,而位带操作其实是读-修改-写操作,只不过在指令级看上去是原子操作而已,位带操作可能会错误的覆盖了外设修改的位
所有  务必清楚位带操作的副作用   51的位操作确是真实的原子操作 这是本质的区别
实际上stm32自带io口位操作的寄存器brr和bsrr,st推荐用这种方法原子的修改单个的位
正点原子已经改用这种方法操作io位,他改用的原因是这种方法io翻转更快
zale1204 发表于 2014-8-16 08:24 来自手机 | 显示全部楼层
楼上几位已经解说的很清楚了⊙﹏⊙
清风吹斜阳 发表于 2016-6-13 17:58 | 显示全部楼层
myxiaonia 发表于 2014-8-12 22:45
轻易的使用外设寄存器位带常常带来巨大的隐患,原子的资料不错,st官方例程更不错,但是那些很多时候仅仅是 ...

请问那个原子改了之后的代码在哪?我找不到那个用BSRR操作的,知道的说下谢谢
天一止水 发表于 2016-12-26 10:35 | 显示全部楼层
清风吹斜阳 发表于 2016-6-13 17:58
请问那个原子改了之后的代码在哪?我找不到那个用BSRR操作的,知道的说下谢谢 ...

找GPIO的GPIO_SetBits和GPIO_ResetBits
清风吹斜阳 发表于 2017-3-1 16:38 | 显示全部楼层
天一止水 发表于 2016-12-26 10:35
找GPIO的GPIO_SetBits和GPIO_ResetBits

谢谢
您需要登录后才可以回帖 登录 | 注册

本版积分规则

4

主题

7

帖子

0

粉丝
快速回复 在线客服 返回列表 返回顶部