/*
* Initialize the stackprotector canary value.
*
* NOTE: this must only be called from functions that never return,
* and it must always be inlined.
*/
static __always_inline void boot_init_stack_canary(void)
{
u64 canary;
u64 tsc; #ifdef CONFIG_X86_64
BUILD_BUG_ON(offsetof(union irq_stack_union, stack_canary) != 40);
#endif
/*
* We both use the random pool and the current TSC as a source
* of randomness. The TSC only matters for very early init,
* there it already has some randomness on most systems. Later
* on during the bootup the random pool has true entropy too.
*/
get_random_bytes(&canary, sizeof(canary));
tsc = __native_read_tsc();
canary += tsc + (tsc << 32UL); current->stack_canary = canary;
#ifdef CONFIG_X86_64
this_cpu_write(irq_stack_union.stack_canary, canary);
#else
this_cpu_write(stack_canary.canary, canary);
#endif
}

该函数主要用于初始化“金丝雀“——canary的值。

用于防止栈溢出攻击。

关于栈溢出攻击,有两篇非常好的文章:
http://www.ibm.com/developerworks/cn/linux/l-overflow/
http://blog.aliyun.com/1126

get_random_bytes获取一个内核随机数,赋值给canary。

__native_read_tsc返回一个与TSC相关的数值。

TSC:Time Stamp Counter,是Linux下三种时钟的一种,也是CPU里面的一个64位的寄存器,每一个CPU时钟周期其数值加1.

canary += tsc + (tsc << 32UL);

终于得到canary的值,并将其赋值给current->stack_canary——当前进程的stack_canary成员。

通常採用两种方法防止栈缓冲溢出:

1 发生栈缓冲溢出时将其检測出来。从而阻止通过恶意代码更改指令指针;

2 未直接检測栈缓冲溢出的情况下,预防恶意代码攻击。

stack canary技术属于第一中方法的一种。在恶意代码运行前,可以发现栈缓冲溢出。

程序启动时,canary的值被保存在函数返回地址之前。大部分栈缓冲溢出攻击是从内存的低位向高位覆写内存,所以为了覆写返回地址。必须覆写canary。

所以在使用返回地址之前,查看canary的值。就行确认是否发生了栈缓冲溢出攻击。

start_kernel——boot_init_stack_canary的更多相关文章

  1. linux源码分析(三)-start_kernel

    前置:这里使用的linux版本是4.8,x86体系. start_kernel是过了引导阶段,进入到了内核启动阶段的入口.函数在init/main.c中. set_task_stack_end_mag ...

  2. 实验三:gdb跟踪调试内核从start_kernel到init进程启动

    原创作品转载请注明出处<Linux内核分析>MOOC课程http://mooc.study.163.com/course/USTC-1000029000 如果我写的不好或者有误的地方请留言 ...

  3. linux源码分析(五)-start_kernel

    前置:这里使用的linux版本是4.8,x86体系. local_irq_disable(); 这个函数是做了关闭中断操作.和后面的local_irq_enable相对应.说明启动的下面函数是不允许被 ...

  4. Linux内核启动过程start_kernel分析

    虽然题目是start_kernel分析,但是由于我在ubuntu环境下配置实验环境遇到了一些问题,我觉得有必要把这些问题及其解决办法写下来. 首先我使用的是Ubuntu14.04 amx64,以下的步 ...

  5. arm linux kernel 从入口到start_kernel 的代码分析

    参考资料: <ARM体系结构与编程> <嵌入式Linux应用开发完全手册> Linux_Memory_Address_Mapping http://www.chinaunix. ...

  6. arm linux kernel启动之start_kernel

    了解完kernel启动以前的汇编之后我们来看看正式的c语言启动代码,也就是我们的start_kernel函数了.start_kernel相当大,里面每一个调用到的函数都足够我们伤脑筋了,我这里只是浅尝 ...

  7. 使用gdb跟踪Linux内核启动过程(从start_kernel到init进程启动)

    本次实验过程如下: 1. 运行MenuOS系统 在实验楼的虚拟机环境里,打击打开shell,使用下面的命令 cd LinuxKernel/ qemu -kernel linux-/arch/x86/b ...

  8. 第3阶段——内核启动分析之start_kernel初始化函数(5)

    内核启动分析之start_kernel初始化函数(init/main.c) stext函数启动内核后,就开始进入start_kernel初始化各个函数, 下面只是浅尝辄止的描述一下函数的功能,很多函数 ...

  9. Linux移植之内核启动过程start_kernel函数简析

    在Linux移植之内核启动过程引导阶段分析中从arch/arm/kernel/head.S开始分析,最后分析到课start_kernel这个C函数,下面就简单分析下这个函数,因为涉及到Linux的内容 ...

随机推荐

  1. 关于在打包Jar文件时遇到的资源路径问题(一)

    当我们将程序写好,并进行打包成Jar文件时,通常都带有各种资源,这些资源可以是图像或者声音文件,也可以是别的如文本文件或二进制文件等,这些资源都和代码密切相关.例如在一个JPanel类上显示一些可能变 ...

  2. 基于visual Studio2013解决面试题之0308Fibonacci数列

     题目

  3. Cocos2dx中Plugin-X 在android下的整合

    直接拉plugin-x中的jar包导入到Eclipse中就可以.用这么麻烦的工具干嘛.

  4. Android broadcast

    发送广播而且接受.发送两个广播 Intent intent = new Intent(); intent.setAction("com.wxq.CUSTOM_INTENT"); s ...

  5. ABP模块设计

    ABP模块设计 返回ABP系列 ABP是“ASP.NET Boilerplate Project (ASP.NET样板项目)”的简称. ASP.NET Boilerplate是一个用最佳实践和流行技术 ...

  6. 用Stack实现对多线程的管理范例

    多线程就是并发技术,当线程数量超过一定数量时,系统响应就会变慢,所以就必须对线程数量进行控制,那么采用哪种控制方法呢?采用Stack类模仿堆栈,之所以说是模仿,就是因为Stack类毕竟不是真实的堆栈, ...

  7. jQuery为啥要提供一个load()方法?

    上午的时候,找个闲暇事件整理之前整理的一些关于jQuery的东西,看到了一个之前做的jQuery的$(document).ready()与window.onload()方法的比較. 上面两个方法最重要 ...

  8. nginx源代码分析--模块分类

    ngx-modules Nginx 基本的模块大致能够分为四类: handler – 协同完毕client请求的处理.产生响应数据.比方模块, ngx_http_rewrite_module, ngx ...

  9. 网络编程Socket之TCP之close/shutdown具体解释(续)

    接着上一篇网络编程Socket之TCP之close/shutdown具体解释 如今我们看看对于不同情况的close的返回情况和可能遇到的一些问题: 1.默认操作的close 说明:我们已经知道writ ...

  10. sql server 2012 数据库还原方法

    USE master RESTORE DATABASE WSS_Content FROM DISK = N'D:\bak\contentbak.bak' WITH REPLACE, NORECOVER ...