linux kernel - task_struct 各个成员 浅析

进程内核栈与进程描述符

task_struct 中部分成员的值 是随着进程的生命周期而动态变化的(如 :进程的状态 unsigned long state...)
先看一幅图:
这里写图片描述

软中断与进程内核栈

看一幅图

这里写图片描述
先从do_softirq()开始说吧,不论是再中断上下文中通过invoke_softirq()处理软中断,还是由中断守护进程ksoftirq来处理,他们都会调用到这个函数,

asmlinkage void do_softirq(void)
{
    /**
        typedef unsigned int __u32

        它是软中断的位图(具体的说 是 __softirq_pending),无符号整形,触发软中断、检查有没有待处理的软中断
        都依据的是这个pending(作者为什么要用一个整形来记录软中断?为什么要这样设计?没有更好的方法了吗?),
        它的值来源于 local_softirq_pending()

        好,下面我们来关注这个函数,看看它的源头活水
    */
    __u32 pending;

    unsigned long flags;
    /*
        如果还处于中断上下文环境中,就return了,为什么?

        它的底层是 这样的一个宏函数 :
        #define irq_count() (preempt_count() & (HARDIRQ_MASK | SOFTIRQ_MASK | NMI_MASK))

        #define preempt_count() (current_thread_info()->preempt_count)

        这个current_thread_info()函数 返回struct thread_info * 是我们重点关注的函数,在下面的代码再说,
    */
    if (in_interrupt())
        return;
    /*
        这个函数 最终调用了一个内嵌了汇编的函数:
            下面是内嵌的汇编代码 : 
             第二行 是 cpsid i 来关闭中断。当然了开中断 就是 cpsie i 指令了
                asm volatile(
                    "   mrs %0, cpsr    @ arch_local_irq_save\n"
                    "   cpsid   i"
                    : "=r" (flags) : : "memory", "cc");
                return flags;       
    */
    local_irq_save(flags);

    /*
        好,真正的演员 闪亮登场了 .............. 下面单独说
    */
    pending = local_softirq_pending();

    /*
        如果有待处理的软中断,就调用__do_softirq()函数处理,

        这个函数不是我们的重点,它的处理过程大致是 :

        我以前的博文写了一点,关于tasklet的,可参考一下
        http://blog.csdn.net/leesagacious/article/details/50500096

        依次检查它的32位,看是否为 1,如果为 1 ,就调用软中断处理函数

        代码 :
        do{
            if(pending & 1)    //检查第一位 是否被 置 1,所以,当pending == 0了,就说明没有待处理的软中断了,
            {
                h->action(h);  // 看! 在这里,软中断处理函数被调用。在这里被调用,在open_softirq()函数先注册好.
            }   

            h++;    
            pending >>= 1;  //pending的位 >> 1位,32位向右都移动一位,丢掉已经检查后的第一位(TASKLET_SOFTIRQ位于第6位),

        }while(pending);

    下面有一幅图,简略描述了一下过程
    */
    if (pending)
        __do_softirq();

    local_irq_restore(flags);
}

这里写图片描述

所以,软中断被调用的条件是 :
        1 : 不在中断上下文中
        2 : local_softirq_pending()返回值不为0,即有待处理的软中断
进程描述符与Linux高速缓存
进程描述符的各个成员

1 : struct files_struct * files;

先看一幅图

这里写图片描述

struct task_struct
{
    struct files_struct * files;
};

struct files_struct{
    /*
        fd_array[]
        里面存放的都是 struct file *,指向打开的文件
        数组下标 就是 在应用空间执行open()函数的返回值
    */
    struct file __rcu * fd_array[NR_OPEN_DEFAULT];
};

struct file{
    /*
        文件操作表,表中是向VFS层提供的接口函数
        用户空间通过设备文件对设备的open()、ioctl()的操作,
        这个表中对应的函数会响应
    */
    const struct file_operations * f_op;
    /*
        文件的引用计数
    */
    atomic_long_t f_count;
    /*
        打开文件时指定的标志
    */
    unsigned int f_flags;
    /*
        访问模式
    */  
    fmode_t f_mode;
    /*
        文件指针位移
    */
    loff_t f_pos;   
    /*
        这个很重要,打开文件的私有数据,你可以把数据暂时存放在这里,
        在需要的地方通过 file->private_data取出来,
        这个技巧,在kernel中使用的很多,一般是在open函数中设置的
    */
    void * private_data;
};

实验验证 (上面的那个图画错了,呜呜…)
这里写图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值