精华内容
下载资源
问答
  • C语言寄存器变量

    千次阅读 2019-01-06 11:21:21
    对于频繁使用的变量可以把它放在寄存器中来提速度。 对于VC编译器会自动优化,即使没有声明寄存器变量,VC也会自动优化。 对于GCC编译器就不会自动优化。 定义一个寄存器变量: void main(){ register int i =...

    寄存器存在于CPU内部,运算速度非常快, 因为内存中的数据必须载入寄存器才能计算。如果直接定义一个变量为寄存器变量,则少了载入等过程自然会快。对于频繁使用的变量可以把它放在寄存器中来提速度。

    对于VC编译器会自动优化,即使没有声明寄存器变量,VC也会自动优化。

    对于GCC编译器就不会自动优化。

    定义一个寄存器变量:

    void main(){
         register int i = 0;
         //&i; //寄存器变量放在cpu中,没有地址, 但是c++中没问题
    }

    接下来,通过gcc编译器来编译下面代码,测试执行速度。 

    #include<stdio.h>
    #include<stdlib.h>
    #include<time.h>
    
    void main4()
    {
        time_t start,end;
        time(&start);//获取当前时间,放在start变量中
    
        //这里用的是gcc的编译器,即这里不会自动优化。
        // 测试如下没有设置寄存器变量,程序运行需要8秒
        //double res = 0.0;//结果
        //long int i = 0;
    
        //定义寄存器变量 ,执行只需要4-5秒,效率高不少。
        register double res = 0.0;
        register long int i = 0;
    
        for (;i<2500000000;i++)
        {
            res += i;
        }
        printf("%f\n",res);
    
        time(&end); //获取当前时间放在end中
    
        printf("%d",(unsigned int)(end - start)); //获取时间差
    }

    通过上面代码可以得出结论,对于频繁使用的变量完全可以给它前面加上关键字register, 定义成寄存器变量。

    最后值得注意下面2点:

    //全局变量最好不要占用寄存器,会影响程序的速度
    register int num = 1000;
    
    //静态变量无法定义为寄存器变量,静态变量存在静态区
    register static double  res = 0.0;

     

    展开全文
  • C语言寄存器变量register

    万次阅读 2015-04-17 15:25:11
    用register声明的变量是寄存器变量,是存放在CPU的寄存器里的。而我们平时声明的变量是存放在内存中的。虽说内存的速度已经很快了,不过跟寄存器比起来还是差得远。 寄存器变量和普通变量比起来速度上的差异很大,...
        用register声明的变量是寄存器变量,是存放在CPU的寄存器里的。而我们平时声明的变量是存放在内存中的。虽说内存的速度已经很快了,不过跟寄存器比起来还是差得远。
        寄存器变量和普通变量比起来速度上的差异很大,毕竟CPU的速度远远大于内存的速度。寄存器有这么两个特点,一个是运算速度快,一个是不能取地址。
        学过C的都应该知道每一个变量在内存中都占有一定的的空间,来存放数据。但是在寄存器中的变量是不能取地址的,编译器会报错。
    

    来我们看看寄存器变量和普通话的变量的速度到底能差多少。

    这段代码用了0.952秒运行

        这段代码运行用了0.952秒
    

    这段代码用了0.094秒运行

        这段代码运行用了0.094秒
    

    差距如此之大。

    实际使用时,底层硬件环境的实际情况对寄存器变量的使用会有一些限制。每个函数中只有很少的变量可以保存在寄存器中,且只允许某些类型的变量。但是,过量的寄存器声明并没有什么害处,这是因为编译器可以忽略过量的或者不支持的寄存器变量声明。另外,无论寄存器变量实际上是不是存放在寄存器中,它的地址都是不能访问的。在不同的机器中,对寄存器变量的数目和类型的具体限制也是不同的。
    ——《C程序设计语言(第二版) Brain W.Kernighan & Dennis M.Ritchie》

    展开全文
  • C语言寄存器操作

    2021-10-30 17:02:50
    C语言寄存器操作

    C语言:寄存器操作

    在对芯片进行开发时,我们对芯片的操作本质上就是对芯片底层寄存器进行操作,在C语言中对寄存器进行操作则是通过寄存器的地址进行数据的赋值,那这个过程是如何实现的呢?

    我们在学习单片机时,会使用到单片机厂商提供 SDK,会遇到如下的代码

    /* 
     * CCM相关寄存器地址 
     */
    #define CCM_CCGR0 			*((volatile unsigned int *)0X020C4068)
    #define CCM_CCGR1 			*((volatile unsigned int *)0X020C406C)
    #define CCM_CCGR2 			*((volatile unsigned int *)0X020C4070)
    #define CCM_CCGR3 			*((volatile unsigned int *)0X020C4074)
    #define CCM_CCGR4 			*((volatile unsigned int *)0X020C4078)
    #define CCM_CCGR5 			*((volatile unsigned int *)0X020C407C)
    #define CCM_CCGR6 			*((volatile unsigned int *)0X020C4080)
    

    这些代码用宏定义来替换掉寄存器的地址,方便用户直接使用宏定义名称来操作寄存器,最关键的部分就是下面这段代码:

    *((volatile unsigned int *)0X020C4068)
    

    这部分代码就是用来映射寄存器,使用 volatile unsigned int * 来将一个寄存器地址强制转化为 unsigned int 的指针,同时使用 volatile 关键字对寄存器地址进行修饰,告诉编译器,该地址运行过程中随时可能变化,编译时不要过优化该地址!

    关于 volatile 的用法可以看我之前的文章: C语言:volatile关键字

    在将寄存器地址强制转化为指针地址后,在前面在加上 * 指向地址存放的值,之后我们直接调用宏定义就可以操作寄存器了,如下

    CCM_CCGR0 = 0xffffffff;
    CCM_CCGR1 = 0xffffffff;
    CCM_CCGR2 = 0xffffffff;
    CCM_CCGR3 = 0xffffffff;
    CCM_CCGR4 = 0xffffffff;
    CCM_CCGR5 = 0xffffffff;
    CCM_CCGR6 = 0xffffffff;
    

    以上一般就是对芯片寄存器进行开发时常用的操作手段

    展开全文
  • c语言常见寄存器操作

    千次阅读 2019-04-24 18:40:55
    1 寄存器地址的定义: #define UART_BASE_ADRS (0x10000000) /* 串口的基地址 */ #define UART_RHR *(volatile unsigned char *)(UART_BASE_ADRS + 0) /* 数据接受寄存器 */ #define UART_THR *(volatile ...

    1 寄存器地址的定义:
        #define UART_BASE_ADRS (0x10000000)     /* 串口的基地址 */
        #define UART_RHR *(volatile unsigned char *)(UART_BASE_ADRS + 0)  /* 数据接受寄存器 */
        #define UART_THR *(volatile unsigned char *)(UART_BASE_ADRS + 0)  /* 数据发送寄存器 */

    2 寄存器读写操作:
        UART_THR = ch; /* 发送数据 */
        ch = UART_RHR; /* 接收数据 */
        也可采用定义带参数宏实现
        #define WRITE_REG(addr, ch) *(volatile unsigned char *)(addr) = ch
        #define READ_REG(addr, ch) ch = *(volatile unsigned char *)(addr)
        
        
    3 对寄存器相应位的操作方法:
        定义寄存器
        #define UART_LCR *(volatile unsigned char *)(UART_BASE_ADRS + 3)  /* 线控制寄存器 */
        
        定义寄存器相应位的值
        #define CHAR_LEN_5 0x00
        #define CHAR_LEN_6 0x01
        #define CHAR_LEN_7 0x02
        #define CHAR_LEN_8 0x03    /* 8 data bit */
        #define LCR_STB  0x04 /* Stop bit control */
        #define ONE_STOP 0x00 /* One stop bit! */
        #define LCR_PEN  0x08 /* Parity Enable */
        #define PARITY_NONE 0x00
        #define LCR_EPS  0x10 /* Even Parity Select */
        #define LCR_SP  0x20 /* Force Parity */
        #define LCR_SBRK 0x40 /* Start Break */
        #define LCR_DLAB 0x80 /* Divisor Latch Access Bit */
        
        定义寄存器相应位的值另一种方法
        #define CHAR_LEN_5 0<<0
        #define CHAR_LEN_6 1<<0
        #define CHAR_LEN_7 1<<1
        #define CHAR_LEN_8 (1<<0)|(1<<1)    /* 8 data bit */
        #define LCR_STB  1<<2 /* Stop bit control */
        #define ONE_STOP 0<<2 /* One stop bit! */
        #define LCR_PEN  1<<3 /* Parity Enable */
        #define PARITY_NONE 0<<3
        #define LCR_EPS  1<<4 /* Even Parity Select */
        #define LCR_SP  1<<5 /* Force Parity */
        #define LCR_SBRK 1<<6 /* Start Break */
        #define LCR_DLAB 1<<7 /* Divisor Latch Access Bit */
        
        对寄存器操作只需对相应位或赋值
        UART_LCR = CHAR_LEN_8 | ONE_STOP | PARITY_NONE;    /* 设置 8位数据位,1位停止位,无校验位 */
        
    4 对寄存器某一位置位与清零
        对某一寄存器第7位置位
        XX_CRTL |= 1<<7;
        XX_CRTL &= ~(1<<7);
           
        UART_LCR |= LCR_DLAB;           /* 时钟分频器锁存使能 */
        UART_LCR &= ~(LCR_DLAB);        /* 禁止时钟分频器锁存 */
        
    5 判断寄存器某一位是否置位或为0的方法
        #define UART_LSR *(volatile unsigned char *)(UART_BASE_ADRS + 5)  /* 线状态寄存器 */
        #define LSR_DR  1<<0 /* Data Ready */
        
        当UART_LSR的第0位为1时结束循环
        while (!(UART_LSR & LSR_DR)) /* 等待数据接收完 */

     

    if (tpreg&(1<<15))    //看tpreg的第15位

    tbuffer = iccurdata ^ ioolddata;//取出改变的io口
    tbufferh = iocurdata & tbuffer;//取出由低变高的io
    tbuffer^=tbufferh;    //取出由高变低的io


    (comm&0x40) &&1;  //comm的bit6位是否为1  

    a=(a&0x0f)^0x0f   //高4位清0,低4位取反  
    a<<4;  //取反的低4位移到高4位

    if(!led)   //led=0
    if(led)  //led=1
    if(!(led_time||led_cnt))   led_time=0且led_cnt=0
    usartxbase |= itmask;//对应位置1
    usartxbase &= ~itmask;//对应位置0


    USART_IT >> 0x08;  //将bit8之后(bit9)的移到低位
    #define IS_USART_DMAREQ(DMAREQ) ((((DMAREQ) & (uint16_t)0xFF3F) == 0x00) && ((DMAREQ) != (uint16_t)0x00))
    //判断bit7 bit6是否不同时为0
     

    展开全文
  • c语言寄存器变量

    2016-08-10 13:46:00
    对于频繁使用的变量可以把它放在寄存器中来提速度。  对于VC编译器会自动优化,即使没有声明寄存器变量,VC也会自动优化。  对于GCC编译器就不会自动优化。  定义一个寄存器变量: 2 3 void main() 4 { ...
  • 目录CPU型号确定寄存器的地址问题GPIO寄存器GPFESLnGPSETnGPCLRn重要函数mmap函数munmap函数点灯程序 平台:树莓派3B 版本: 2021-05-07-raspios-buster-armhf CPU型号确定 由 pinout 命令可知,所用的板子Soc...
  • C语言寄存器变量

    2020-01-05 00:27:48
    文章目录1、寄存器变量2、寄存器变量速度测试 ...因此,C语言\C++语言还定义了一种变量,不是保存在内存上,而是直接存储在CPU中的寄存器中,这种变量称为寄存器变量。 register int i=100; C编译程序会自动...
  • C语言寄存器的位操作

    千次阅读 2020-08-30 12:18:36
    C语言位操作 1、位操作符 (1)位与& 逻辑与&& 1&1=1 1&0=0 0&0=0 0&1=0 (2)位或 | 逻辑或 || 1 | 1=1 1 | 0=1 0 | 0=0 0 | 1=1 (3)位取反~ 逻辑取反 ! (4)位...
  • int main() { for (int i = 0; i < 10; i++) { register int a = i;// register 是寄存器 当执行完for循环后 a的内存空间会自动释放 printf("a:%i",a); } system("pause"); return 0; }
  • 单片机的特殊功能寄存器SFR,是SRAM地址已经确定的SRAM单元,在C语言环境下对其访问归纳起来有两种方法。
  • C语言位操作在寄存器中的应用 本文参考另一篇博客写成附链接,个人感觉内容过多不便于吸收,就写了这篇博客。 整体思想: 设置一个位就是设置该位为1,清除就是设置该位为0 寄存器操作的要求:特定位改变而不影响...
  • C语言寄存器变量与内存变量
  • C语言函数与栈、寄存器的关系

    千次阅读 2018-09-25 22:32:36
    最近想学PWN,虽然这些是之前学过的,但是在做题的时候发现细节的重要性,就决定回顾一遍,这里写的主要也就是给自己记录一下,加深映像,同时加了一些...上来肯定事先了解一下寄存器啦,如下图 这里就先说一下ES...
  • 32单片机C语言相关知识以及寄存器地址名称映射分析
  • C语言参数传递所使用寄存器

    千次阅读 2020-02-09 13:12:53
    探索下C语言的函数是如何传递参数的,寄存器?栈?,何时使用寄存器使用哪些寄存器,什么时候使用栈来传递参数。这是容易疑惑的地方。 用gcc编译C程序,看看C语言是如何传递参数的。同时用到了edb调试器。使用的...
  • 第6章 使用C语言操作DSP的寄存器 北京航空航天大学出版社 作者顾卫钢 北京航空航天大学出版社 作者顾卫钢 电信学院张 蕾 DSP原理及应用 6.1 寄存器C语言访问 特殊的存储单元具有特殊的功能具体的含义 DSP通过对...
  • 使用C语言操作寄存器前,仍需要先分析《开发板原理图》和《参考手册》,从而得知需要操作哪些外设寄存器,假设读者已经了解需要操作哪些外设寄存器。 本章涉及的代码位于100ASK_STM32F103开发板资料的“5_程序源码...
  • 使用C语言来访问ARM寄存器的语法

    千次阅读 2019-12-25 09:58:04
    ARM寄存器的地址类似于内存地址(IO与内存统一编址的),所以这里的问题是用C语言读写寄存器,就是用C语言来读写内存地址。用C语言来访问内存,就要用到指针:例如某寄存器的地址为0xE0200240; define GPJ0CON 0xE...
  • 使用c语言打印x86寄存器

    千次阅读 2017-08-18 11:20:03
    使用c语言打印x86寄存器void main() { int out = 0; asm ("movl %%ecx, %0\n" : "=r"(out)); printf("ecx is %x\n",out); int seg; asm volatile("movw %%fs,%0" : "=rm" (seg)); printf("fs is %x\n
  • C语言-寄存器和内存

    千次阅读 2010-11-12 17:05:00
    寄存器是CPU内部...   C语言可以把变量定义为寄存器类型的,将数据直接存放在CPU的寄存器中,使用关键字register定义变量。 例如register a=123;定义a为寄存器类型变量。   对于reg
  • C语言如何实现读写SOC中的寄存器

    千次阅读 2019-08-31 17:42:33
    C语言如何实现读写SOC中的寄存器 SOC、MCU、MPU等处理芯片,芯片内部有大量的...对于汇编语言,可以使用汇编指令操作寄存器,同样,C语言也具备操作寄存器能力。 一、操作单个寄存器 比如需要初始化寄存器LCDC...
  • 网上的文章有的说C语言调用函数参数使用栈传递,有的说使用寄存器传递。那么到底参数是使用栈还是寄存器呢? 先说结论: 32位程序使用栈传递 64位程序根据参数的个数而不同 参数1~6个,使用寄存器传递 参数大于6个...
  • #include<reg51.h>//头文件 void main() { P3=0XBF; (怎么把这组数据存起来。 ) P3=0xFF; (还有这一组数据也存起来。) { P2= ( 怎么把上面两组数据调出 在相与, P2... 小弟不会使用寄存器。 谢谢
  • c语言自定义寄存器操作的一些方法

    千次阅读 2011-10-26 09:12:42
    1 寄存器地址的定义:  #define UART_BASE_ADRS (0x10000000) /* 串口的基地址 */  #define UART_RHR *(volatile unsigned char *)(UART_BASE_ADRS + 0) /* 数据接受寄存器 */  #define UART_THR *(volatile...
  • (1)生成序列:使用#include库构造序列,使用bint.to_string()将输入的01串转成字符串,用str暂存。将bint[3]和bint[0]异或,赋值给bint[4]也就是a5,循环左移,将bint转成字符串后s1[4]就是生成的a1,将 a1添加到s2...
  • 第6章 使用C语言操作DSP的寄存器 6.1 寄存器C语言访问 由于DSP的寄存器能够实现对系统和外设功能的配置与控制因此在DSP的开发过程中对于寄存器的操作是极为重要的也是很频繁的也就是说对寄存器的操作是否方便会...
  • 寄存器值: u32RegValue = *((uint32 volatile *)(reg_addres)); 写寄存器值: *((uint32 volatile *)(reg_addres)) = value;
  • c语言关键字之寄存器变量registerregister 在C语言中存储类型说明符register修饰变量时,暗示程序中相应的变量将经常被使用,如果可能的话将其保存在CPU的寄存器中,以此加快存储速度。register建议编译器将相应...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 83,068
精华内容 33,227
关键字:

c语言寄存器的使用

c语言 订阅