想要修改ARM芯片的时钟,需要去查询芯片手册和原理图,获取相关的信息(见下方图片)

首先来看时钟的结构图


根据结构图可以看出,时钟源有两种选择:1. XTIpll和XTOpll所连接的晶振

                   2. EXTCLK引脚外接一个时钟源


OM[3:2]用来选择到底使用哪个时钟源


再查看原理图,可以发现:OM3和OM2硬件上都是接GND,所以可以知道:采用12MHz晶振作为时钟源


阅读芯片手册,还可以查询到其他寄存器的相关信息,见下图:

JZ2440内部使用三种时钟:

            FCLK: 用于ARM920T芯片,即CPU

            HCLK:通过AHB总线,提供给ARM920T芯片、内存控制器,中断控制器,LCD控制器等等

            PCLK:   通过APB总线,提供给一些外围设备使用,如WDT,IIS,I2C等等


FCLK通过HDIVN分频得到HCLK,通过PDIVN分频得到PCLK,这里设置FCLK:HCLK:PCLK=400MHz : 100MHz : 50Hz

   1、修改MPLLCON寄存器中MDIV ,PDIV ,SDIV的值为92 ,1 ,1,可以得到FCLK为400MHz

   2、修改CLKDIVN中,HDIVN和PDIVN分别为0b10和1,使得HCLK=FCLK/4 , PCLK=HCLK/2


阅读芯片手册中,晶振作为时钟源的时序图,可以发现,当配置PLL时,会有一个LOCKTIME时间,用来等待输出的FCLK频率稳定


在这里,不对LOCKTIME进行修改,仍然使用它的默认值0xFFFFFFFF


继续阅读芯片手册,有一个备注信息:

    当HDIVN不是0且CPU工作于快速总线模式的时候,CPU会采用HCLK作为它的时钟频率,

    因此如果想让HDIVN修改后,CPU采用FCLK,必须添加下方代码,让CPU工作于异步模式 

      mrc p15,0,r0,c1,c0,0
      orr r0,r0,#R1_nF:OR:R1_iA                      
      mcr p15,0,r0,c1,c0,0

【代码  #R1_nF:OR:R1_iA 的意思】———— 点我

对时钟修改的分析就大致差不多了,接下来写汇编文件实现要求

.text
.global _start _start: /* 关闭看门狗,如果不关闭,系统会自动重启 */
ldr r0,=0x53000000
ldr r1,=
str r1,[r0]
/* 修改时钟,FCLK=400MHz,HCLK=100MHz,PCLK=50MHz */ /* 设置配置MPLL时的LOCKTIME时间为默认值 */
ldr r0,=0x4c000000
ldr r1,=0xFFFFFFFF
str r1,[r0] /* 设置FCLK:HCLK:PCLK=8:2:1 */
ldr r0,=0x4c000014
ldr r1,=0x5
str r1,[r0] /* 设置CPU工作于异步模式
** 如果不作此设置,当HDIVN不是0时,CPU会采用HCLK的频率而不是采用FCLK的频率
*/
mrc p15,,r0,c1,c0,
orr r0,r0,#0xc0000000 // #R1_nF:OR:R1_iA等价于#0xc0000000
mcr p15,,r0,c1,c0, /* 设置MPLL的PMS,使得FCLK=400MHz
** m = MDIV+8 = 92+8=100
** p = PDIV+2 = 1+2 = 3
** s = SDIV = 1
** FCLK = 2*m*Fin/(p*2^s) = 2*100*12/(3*2^1)=400MHz
*/
ldr r0,=0x4C000004
ldr r1,=(<<)|(<<)|(<<)
str r1,[r0]
/* 设置好PLL之后,就会锁定lock time,直到PLL稳定输出 */
/* cpu会工作于新的频率FCLK /* 判断是nor启动还是nand启动
** 先把0地址原来的值读取出来,保存到r0寄存器中
** 再把0写入0地址对应的内存单元,之后读取0地址内存单元的值
** 如果读取出来的值与原来的值不一致,说明是nor启动
** 如果读取出来的值与原来的值一致,说明是nand启动,此时需要修改栈的地址
*/ mov r1,#
ldr r0,[r1] // 读取原来的值,备份一下
str r1,[r1] // 把0写入0地址
ldr r2,[r1] // 读取0地址新的值
cmp r2,r0 // 如果r0和r2的值一样,说明是nand启动,此时修改sp的值 /* 设置栈:sp */ ldr sp,=0x40000000+ // 先默认nor启动//
moveq sp,# // 如果r2=r1,把4096传给sp,改为nand启动
streq r0,[r1] // 如果r2=r1,恢复0地址原来的值
bl main // 跳转到main函数
halt:
b halt // 不停的跳转到halt,相当于死循环,方便观察效果

另外再附上JZ2440开发板3盏LED灯循环点亮的C程序(和按键点亮LED灯需要知道的知识差不多,这里不再作分析),用来观察时钟修改后的效果

#include "s3c2440_soc.h"
void delay(volatile int d) //延时函数
{
while(d--);
}
int main(void)
{
/*设置GPFCON的GPF4/5/6,让它们变成输出引脚*/
GPFCON &=~((<<)|(<<)|(<<)); //先让GPFCON的GPF4/5/6清零
GPFCON |=((<<)|(<<)|(<<)); //配置好GPFCON的GPF4/5/6,让它们变成输出引脚 /*循环点亮3盏灯*/
int val=,tmp; //val取值范围0b000~0b111,刚好三盏灯
while()
{ tmp=~val; //因为val为0的时候,灯会由亮到灭,所以这里需要取反,才能让灯从灭到亮
tmp &=; //只需要三位的值就好了
GPFDAT &=~(<<); //GPFDAT寄存器先清零,因为是4,5,6位,所以这里7左移4位就可以
GPFDAT |=(tmp<<);
delay(); //加上一个延时,不然灯切换太快了,看不出来
val++;
if(val==)
{
val=;
}
} return ;
}

上传到 linux,编译得到 led.bin文件,烧写到开发板之后,发现LED灯切换得比以前快多了,因为CPU是400MHz了,ARM芯片时钟修改成功。


JZ2440开发板:修改ARM芯片时钟(学习笔记)的更多相关文章

  1. JZ2440开发板:UART(串口)使用(学习笔记)

    查看UART在硬件上的信息,阅读JZ2440原理图可以看到: JZ2440开发板的UART0是可以跟USB相接的,用于打印调试,UART1,UART2两个串口用来外接模块.所以本文仅对UART0进行操 ...

  2. Linux学习 :移植U-boot_2016.09到JZ2440开发板

    一.下载源码:ftp://ftp.denx.de/pub/u-boot/ 二.初始化编译: ①新建一个单板: cd board/samsung/ cp smdk2410 smdk2440 -rf   ...

  3. Linux学习 :移植U-boot_2012.04.01到JZ2440开发板

    一.下载U-boot源码:ftp://ftp.denx.de/pub/u-boot/ 二.uboot的启动过程: 部分硬件初始化——>加载完整uboot到RAM——>跳转到第二阶段入口开始 ...

  4. JZ2440开发板:用按键点亮LED灯(学习笔记)

    本文是对韦东山嵌入式第一期学习的记录之一,如有您需要查找的信息,可以继续往下阅读. 想要用按键点亮LED灯,就需要知道按键和LED灯的相关信息,这样才可以进行之后的操作.阅读JZ2440的原理图,可以 ...

  5. buildroot构建项目(三)--- u-boot 2017.11 适配开发板修改 1

    当前虽然编译成功了,但是对于我们自己的目标板并不太适用.还得做一系列得修改. 一.lds 文件分析 u-boot 中最重要得链接文件即是,u-boot.lds.我们可以查看我们编译出来得 u-boot ...

  6. 基于JZ2440开发板编写bootloader总结(一)

    凡走过必留下痕迹,学点什么都会有用的. 本系列博文总结了自己在学习嵌入式Linux编程过程中的收获,若有错误,恳请指正,谢谢! --参考教材韦东山系列教材 bootloader 是一个用于启动linu ...

  7. buildroot构建项目(四)--- u-boot 2017.11 适配开发板修改 2 ---- 系统启动初始化之一

    一.代码分析 上一节已经分析了链接文件,知道了首先代码是从 _start 开始,之后设置了中断向量表,然后从 start.s 开始运行. _start:vectors.S (arch\arm\lib) ...

  8. Jz2440开发板熟悉

    title: Jz2440开发板熟悉 tags: ARM date: 2018-10-14 15:05:56 --- 概述 外部晶振为12M Nand Flash 256M,Nor Flash 2M, ...

  9. 第010课_掌握ARM芯片时钟体系

    from:第010课_掌握ARM芯片时钟体系 第001节_S3C2440时钟体系结构 S3C2440是System On Chip(SOC),在芯片省不仅仅有CPU,还有一堆外设. 至于有哪些外设,可 ...

随机推荐

  1. 查看dump oracle数据块查看

    alter system dump datafile 8 block 2523; Block dump from disk:buffer tsn: 87 rdba: 0x160dd924 (88/90 ...

  2. (原)使用 memcache 使用过程中可能遇到的问题

    在项目优化中,使用到了memcache,刚开始不能用,后来期间总会偶尔抛出异常,刚开始怀疑动态库版本问题,后来尝试了各种替换依旧误解,搞得我日思夜想的,天天惦记着他..=_= 下午拿出半天时间,进行错 ...

  3. Hibernate关于父类子类的映射

    怕忘记,把栗子贴上来 以Person类和Student类为例 public class Person { private Integer id; private String name; privat ...

  4. Hibernate双向一对多、双向多对多关联关系中的映射文件怎么写

    这里以一对多关联关系为例.以Country类为一端,Competition类为多端. 一个国家可以有多个赛事,但是一个赛事只能属于一个国家. Country类 public class Country ...

  5. mysql配置远程登录

    1.vim /etc/my.cnf注释这一行:bind-address=127.0.0.1 ==> #bind-address=127.0.0.1 2.重启服务:sudo service mys ...

  6. BZOJ 3399 [Usaco2009 Mar]Sand Castle城堡:贪心【最小匹配代价】

    题目链接:http://www.lydsy.com/JudgeOnline/problem.php?id=3399 题意: 给你一个数列a,和一个可变换顺序的序列b(数列长度≤25000). a增加一 ...

  7. MyBatis框架(4)全局文件

    本次全部学习内容:MyBatisLearning   全局配置文件(本次案例中):

  8. phpstorm下TODO注释

    TODO注释 什么是TODO注释? 标记的注释,表示你代办的任务. 作用 标记你需要编写的任务位置 使用方法 TODO: + 说明: 如果代码中有该标识,说明在标识处有功能代码待编写,待实现的功能在说 ...

  9. Linux下rm -rf删除文件夹报错_ Device or resource busy

    1.错误信息 rm: cannot remove `speechd-centos_6.2-prtl-pred-mf34/modules/t2p/py/third/g2p/.nfs00000000039 ...

  10. Android 进价5_自定义广播 通过广播更新ListView的适配器 下载管理

    1.在处理下载管理时,服务在后台运行,下载完成后要更新listview列表的按钮,将“下载”改成“打开”这样一个功能. 在Activity里面写一个静态内部类,继承广播.其中属性text_button ...