`
izuoyan
  • 浏览: 8916915 次
  • 性别: Icon_minigender_1
  • 来自: 上海
社区版块
存档分类
最新评论

ARM linux系统调用的实现原理

阅读更多

大家都知道linux的应用程序要想访问内核必须使用系统调用从而实现从usr模式转到svc模式。下面咱们看看它的实现过程。

系统调用是os操作系统提供的服务,用户程序通过各种系统调用,来引用内核提供的各种服务,系统调用的执行让用户程序陷入内核,该陷入动作由swi软中断完成。

at91rm9200处理器对应的linux2.4.19内核系统调用对应的软中断定义如下:
#if defined(__thumb__) //thumb模式
#define __syscall(name) \
"push {r7}\n\t" \
"mov r7, #" __sys1(__NR_##name) "\n\t" \
"swi 0\n\t" \
"pop {r7}"
#else //arm模式
#define __syscall(name) "swi\t" __sys1(__NR_##name) "\n\t"
#endif

#define __sys2(x) #x
#define __sys1(x) __sys2(x)
#define __NR_SYSCALL_BASE 0x900000 //此为OS_NUMBER << 20运算值
#define __NR_open (__NR_SYSCALL_BASE+ 5) //0x900005

举一个例子来说:open系统调用,库函数最终会调用__syscall(open),宏展开之后为swi #__NR_open,即,swi #0x900005触发中断,中断号0x900005存放在[lr,#-4]地址中,处理器跳转到arch/arm/kernel/entry-common.S中vector_swi读取[lr,#-4]地址中的中断号,之后查询arch/arm/kernel/entry-common.S中的sys_call_table系统调用表,该表内容在arch/arm/kernel/calls.S中定义,__NR_open在表中对应的顺序号为
__syscall_start:
...
.long SYMBOL_NAME(sys_open) //第5个
...

将sys_call_table[5]中内容传给pc,系统进入sys_open函数,处理实质的open动作

注:用到的一些函数数据所在文件,如下所示

arch/arm/kernel/calls.S声明了系统调用函数

include/asm-arm/unistd.h定义了系统调用的调用号规则
vector_swi定义在arch/arm/kernel/entry-common.S
vector_IRQ定义在arch/arm/kernel/entry-armv.S
vector_FIQ定义在arch/arm/kernel/entry-armv.S
arch/arm/kernel/entry-common.S中对sys_call_table进行了定义:
.type sys_call_table, #object
ENTRY(sys_call_table)
#include "calls.S" //将calls.S中的内容顺序链接到这里
源程序:
ENTRY(vector_swi)
save_user_regs
zero_fp
get_scno //将[lr,#-4]中的中断号转储到scno(r7)
arm710_bug_check scno, ip
#ifdef CONFIG_ALIGNMENT_TRAP
ldr ip, __cr_alignment
ldr ip, [ip]
mcr p15, 0, ip, c1, c0 @ update control register
#endif
enable_irq ip

str r4, [sp, #-S_OFF]! @ push fifth arg

get_current_task tsk
ldr ip, [tsk, #TSK_PTRACE] @ check for syscall tracing
bic scno, scno, #0xff000000 @ mask off SWI op-code
//#define OS_NUMBER 9[entry-header.S]
//所以对于上面示例中open系统调用号scno=0x900005
//eor scno,scno,#0x900000
//之后scno=0x05
eor scno, scno, #OS_NUMBER << 20 @ check OS number
//sys_call_table项为calls.S的内容
adr tbl, sys_call_table @ load syscall table pointer
tst ip, #PT_TRACESYS @ are we tracing syscalls?
bne __sys_trace

adrsvc al, lr, ret_fast_syscall @ return address
cmp scno, #NR_syscalls @ check upper syscall limit
//执行sys_open函数
ldrcc pc, [tbl, scno, lsl #2] @ call sys_* routine
add r1, sp, #S_OFF
2: mov why, #0 @ no longer a real syscall
cmp scno, #ARMSWI_OFFSET
eor r0, scno, #OS_NUMBER << 20 @ put OS number back
bcs SYMBOL_NAME(arm_syscall)
b SYMBOL_NAME(sys_ni_syscall) @ not private func
/*
* This is the really slow path. We're going to be doing
* context switches, and waiting for our parent to respond.
*/
__sys_trace:
add r1, sp, #S_OFF
mov r0, #0 @ trace entry [IP = 0]
bl SYMBOL_NAME(syscall_trace)
/*
//2007-07-01 gliethttp [entry-header.S]
//Like adr, but force SVC mode (if required)
.macro adrsvc, cond, reg, label
adr\cond \reg, \label
.endm
//对应反汇编:
//add lr, pc, #16 ; lr = __sys_trace_return
*/
adrsvc al, lr, __sys_trace_return @ return address
add r1, sp, #S_R0 + S_OFF @ pointer to regs
cmp scno, #NR_syscalls @ check upper syscall limit
ldmccia r1, {r0 - r3} @ have to reload r0 - r3
ldrcc pc, [tbl, scno, lsl #2] @ call sys_* routine
b 2b

__sys_trace_return:
str r0, [sp, #S_R0 + S_OFF]! @ save returned r0
mov r1, sp
mov r0, #1 @ trace exit [IP = 1]
bl SYMBOL_NAME(syscall_trace)
b ret_disable_irq

.align 5
#ifdef CONFIG_ALIGNMENT_TRAP
.type __cr_alignment, #object
__cr_alignment:
.word SYMBOL_NAME(cr_alignment)
#endif
.type sys_call_table, #object
ENTRY(sys_call_table)
#include "calls.S"
(作者:刘洪涛,华清远见嵌入式培训中心讲师)

分享到:
评论

相关推荐

    嵌入式系统/ARM技术中的ARM linux系统调用的实现原理

     大家都知道linux的应用程序要想访问内核必须使用系统调用从而实现从usr模式转到svc模式。下面咱们看看它的实现过程。  系统调用是os操作系统提供的服务,用户程序通过各种系统调用,来引用内核提供的各种服务,...

    ARM-Linux系统移植

    2.1.2 Linux操作系统 .......................................................................................................8 2.1.3 目标板最后运行的环境..................................................

    嵌入式Linux ARM开发课件第六讲

    Uclinux,mizilinux系统引导程序bootloader原理和实现过程:Uboot、vivi等 ARM系统空间划分及系统映射方法 bootloader内核下载模式实现 :tftp、Xmoden linux操作系统原理及组成 介绍linux系统目录组织结构 linux ...

    嵌入式Linux 开发ARM课件第一讲

    万龙44b0 开发板是专门为arm 开发的实验板,这了有十一节基于此的课堂PPT其中有: ...ARMlinux移植过程。 引导程序Uboot移植。 最小系统启动开发过程。 嵌入式文件系统移植:ramdisk、JFFS2、yaff 等等内容相当丰富哦!

    嵌入式Linux ARM开发课件第十一讲

    Uclinux,mizilinux系统引导程序bootloader原理和实现过程:Uboot、vivi等 ARM系统空间划分及系统映射方法 bootloader内核下载模式实现 :tftp、Xmoden linux操作系统原理及组成 介绍linux系统目录组织结构 linux ...

    嵌入式Linux ARM开发课件第九讲

    Uclinux,mizilinux系统引导程序bootloader原理和实现过程:Uboot、vivi等 ARM系统空间划分及系统映射方法 bootloader内核下载模式实现 :tftp、Xmoden linux操作系统原理及组成 介绍linux系统目录组织结构 linux ...

    嵌入式Linux ARM开发课件第三讲

    Uclinux,mizilinux系统引导程序bootloader原理和实现过程:Uboot、vivi等 ARM系统空间划分及系统映射方法 bootloader内核下载模式实现 :tftp、Xmoden linux操作系统原理及组成 介绍linux系统目录组织结构 linux ...

    嵌入式Linux ARM开发课件第十讲

    Uclinux,mizilinux系统引导程序bootloader原理和实现过程:Uboot、vivi等 ARM系统空间划分及系统映射方法 bootloader内核下载模式实现 :tftp、Xmoden linux操作系统原理及组成 介绍linux系统目录组织结构 linux ...

    嵌入式Linux ARM开发课件第五讲

    Uclinux,mizilinux系统引导程序bootloader原理和实现过程:Uboot、vivi等 ARM系统空间划分及系统映射方法 bootloader内核下载模式实现 :tftp、Xmoden linux操作系统原理及组成 介绍linux系统目录组织结构 linux ...

    嵌入式Linux ARM开发课件第八讲

    Uclinux,mizilinux系统引导程序bootloader原理和实现过程:Uboot、vivi等 ARM系统空间划分及系统映射方法 bootloader内核下载模式实现 :tftp、Xmoden linux操作系统原理及组成 介绍linux系统目录组织结构 linux ...

    嵌入式Linux ARM开发课件第二讲

    Uclinux,mizilinux系统引导程序bootloader原理和实现过程:Uboot、vivi等 ARM系统空间划分及系统映射方法 bootloader内核下载模式实现 :tftp、Xmoden linux操作系统原理及组成 介绍linux系统目录组织结构 linux ...

    嵌入式Linux ARM开发课件第四讲

    Uclinux,mizilinux系统引导程序bootloader原理和实现过程:Uboot、vivi等 ARM系统空间划分及系统映射方法 bootloader内核下载模式实现 :tftp、Xmoden linux操作系统原理及组成 介绍linux系统目录组织结构 linux ...

    嵌入式Linux ARM开发课件第七讲

    Uclinux,mizilinux系统引导程序bootloader原理和实现过程:Uboot、vivi等 ARM系统空间划分及系统映射方法 bootloader内核下载模式实现 :tftp、Xmoden linux操作系统原理及组成 介绍linux系统目录组织结构 linux ...

    基于ARM-linux的简易电子相册c源码+项目说明(课程设计).zip

    实现原理: 将要播放的图片存储在二维数组中,在线程中循环读取图片的内容,并写入到开发板的屏幕。在主线程中,循环读取来自触摸屏的事件,通过点击或者滑动屏幕,可实现左右翻页,同时短暂终止循环播放,5s内触摸屏...

    ARM应用系统开发详解

    第3章 ARM微处理器的指令系统 3.1 ARM微处理器的指令集概述 3.1.1 ARM微处理器的指令的分类与格式 3.1.2 指令的条件域 3.2 ARM指令的寻址方式 3.2.1 立即寻址 3.2.2 寄存器寻址 3.2.2 寄存器间接寻址 3.2.3 基址变址...

    嵌入式Linux C编程入门(第2版) PPT

    9.1 linux系统调用及用户编程接口(api) 257 9.1.1 系统调用 257 9.1.2 用户编程接口(api) 257 9.1.3 系统命令 258 9.2 arm linux文件i/o系统概述 258 9.2.1 虚拟文件系统(vfs) 258 9.2.2 通用...

    Linux内核工作原理 word版本 强烈推荐

    大多数Linux核心工作在基于Intel处理器的系统上,但非Intel系统的Linux用户也越来越多。它们是Alpha AXP, ARM, MIPS, Sparc与Power PC。 虽然我可以根据上叙任何一种平台来编写本书的内容,但是我的技术知识与背景...

    千万字肝翻Linux内核源码,对底层原理深耕深分析,从入门到入狱

    内存屏障、内存映射、同步机制、GDB基本功能、CPU缓存、内核启动流程、 syncookie、读写分析、NFS实现框架、网络新特性、skb核心操作、HASH算法、过滤...软硬中断区别、等待队列、字符设备驱动、系统调用、内存碎片。

    基于ARM Cortex-A8和Android 4.x的联动报警系统 (Android 、A8、Linux、驱动、NDK)

    第二部分内容,先简单讲解Android系统移植相关原理,然后一步步手把手教大家如何进行Linux内核移植、Android源码编译、以及Android到Cortex A8开发板的移植;第三部分内容,先教大家如何搭建裸机开发环境,然后带领...

Global site tag (gtag.js) - Google Analytics