加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 综合聚焦 > 服务器 > Linux > 正文

在linux中计算页面错误导致混乱的结果

发布时间:2020-12-14 01:40:33 所属栏目:Linux 来源:网络整理
导读:我正在编写程序来计算 linux系统中页面错误的时间.更确切地说,时间内核执行函数__do_page_fault. 不知怎的,我写了两个全局变量,名为pfcount_at_beg和pfcount_at_end,当函数__do_page_fault在函数的不同位置执行时,它会增加一次. 为了说明,修改后的功能如下:
我正在编写程序来计算 linux系统中页面错误的时间.更确切地说,时间内核执行函数__do_page_fault.
不知怎的,我写了两个全局变量,名为pfcount_at_beg和pfcount_at_end,当函数__do_page_fault在函数的不同位置执行时,它会增加一次.

为了说明,修改后的功能如下:

unsigned long pfcount_at_beg = 0;
unsigned long pfcount_at_end = 0;
static void __kprobes
__do_page_fault(...)
{
    struct vm_area_sruct *vma;
    ...    // VARIABLES DEFINITION 
    unsigned int flags = FAULT_FLAG_ALLOW_RETRY | FAULT_FLAG_KILLABLE;   
    pfcount_at_beg++;        // I add THIS
    ...
    ... 
    // ORIGINAL CODE OF THE FUNCTION
    ...
    pfcount_at_end++;        // I add THIS
}

我预计pfcount_at_end的值小于pfcount_at_beg的值.

因为,我认为,每次内核执行代码pfcount_at_end的指令时,它必须执行pfcount_at_beg(每个函数都从代码的最开始处开始).
另一方面,由于这两行代码之间存在许多条件返回.

然而,结果反过来说. pfcount_at_end的值大于pfcount_at_beg的值.
我使用printk通过自定义的系统调用来打印这些内核变量.我编写了用户级程序来调用系统调用.

这是我简单的系统调用和用户级程序:

// syscall
asmlinkage int sys_mysyscall(void)
{
    printk( KERN_INFO "total pf_at_beg%luntotal pf_at_end%lun",pfcount_at_beg,pfcount_at_end)
    return 0;
}

// user-level program
#include<linux/unistd.h>
#include<sys/syscall.h>
#define __NR_mysyscall 223
int main()
{
    syscall(__NR_mysyscall);
    return 0;
}

有谁知道这期间究竟发生了什么?

刚才我修改了代码,使pfcount_at_beg和pfcount_at_end静态.但是结果没有改变,即pfcount_at_end的值大于pfcount_at_beg的值.
因此可能是由增量的原子内操作引起的.如果我使用读写锁定会更好吗?

解决方法

运算符不保证是原子的,因此您的计数器可能会遇到并发访问并且值不正确.您应该将增量保护为关键部分,或者使用< asm / atomic.h>中定义的atomic_t类型及其相关的atomic_set()和atomic_add()函数(以及更多).

没有直接连接到您的问题,但使用特定的系统调用是过度的(但也许这是一个练习).一个较轻的解决方案可能是使用/ proc条目(也是一个有趣的练习).

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读