加载中…
个人资料
李旭瑞_ECNU
李旭瑞_ECNU
  • 博客等级:
  • 博客积分:0
  • 博客访问:4,798
  • 关注人气:82
  • 获赠金笔:0支
  • 赠出金笔:0支
  • 荣誉徽章:
正文 字体大小:

[转载]DSP_5_DSP/BIOS_例程分析_同优先级用户任务切换

(2012-12-14 22:22:34)
标签:

转载

分类: DSP


这是在网上找的一个DSP/BIOS同优先级任务切换的例程。

CPUDM642。用CCS3.3软件仿真。

Configuration里添加了三个用户任务TSK0~2,优先级都设为1,任务处理函数都设为task,任务参数(task  function argument1)依次设为0 1 2

 http://s10/middle/533d3f4f4bb07c663c279&690

 

 

代码:

 

 

#include <std.h>

 

#include <log.h>

#include <sys.h>

 

#include "switestcfg.h"

 

Void main()

{   ;

}

 

Void task(Arg id_arg)  

 

{

    Int     id = ArgToInt (id_arg); 

    Int     i;  

   

LOG_printf(&trace, "start %d", id);

 

   

    for (i = 0; i < 5 ; i++) {

   

        LOG_printf(&trace, "Loop %d: Task %d Working", i, id);

     

        TSK_yield();

}

  

     LOG_printf(&trace, "Task %d DONE", id);

}

 

 

本例中main函数为空。

在所有DSP/BIOS模块初始化之后,调用main函数。此时硬件中断和软件中断都是禁止的。然后程序开始执行任务函数。

 

首先TSK0调用task函数,任务号id=0,在trace窗口中显示start0,然后进入for循环,

又执行语句LOG_printf(&trace, "Loop %d: Task %d Working", i, id);

 

i=0trace窗口显示Loop 0Task 0 Working

 

TSK_yield函数将TSK0挂起,任务切换到TSK1

 

TSK1也调用task函数,任务号id=1,在trace窗口中显示start1,然后也进入for循环,i=0trace窗口显示Loop 0:Task 1 Working

 

TSK_yield函数将TSK1挂起,任务切换到TSK2

 

TSK1还调用task函数,任务号id=2,在trace窗口中显示start2,然后也进入for循环,i=0trace窗口显示Loop 0Task 2 Working

 

TSK_yield函数将TSK2挂起,任务循环切换回到TSK0

 

TSK0第二次调用task函数,这时下面三条语句

Int     id = ArgToInt (id_arg);

Int     i; 

LOG_printf(&trace, "start %d", id);

就不再执行了。

且在for循环中i=0的情况也不再执行了。

因为TSK0第一次执行的时候那三条语句和for循环中i=0的情况都已经执行过了,TSK0被切换的时候这个任务并没有执行完毕也不是被停止,而是被暂时挂起,就相当于在TSK0被切换的时候自动记忆了一个断点,当再次执行TSK0的时候,这个任务就从上次的那个断点出开始继续往下执行。

 

所以TSK0再次开始执行的时候 i++

i=1, trace窗口显示Loop 1Task 0 Working

 

TSK_yield函数再次将TSK0挂起,任务切换到TSK1

 

同理TSK1再次开始执行的时候i++

i=1, trace窗口显示Loop 1Task 1 Working

 

TSK_yield函数再次将TSK1挂起,任务切换到TSK2

 

同理TSK2再次开始执行的时候i++

i=1, trace窗口显示Loop 1Task 2 Working

 

TSK_yield函数将TSK2挂起,任务再次循环切换回到TSK0

 

如此循环······

 

TSK0i=5时跳出for循环执行最后一条语句LOG_printf(&trace, "Task %d DONE", id);

Trace窗口显示Task 0 DONE

 

TSK1i=5时跳出for循环

Trace窗口显示Task 1 DONE

 

TSK2i=5时跳出for循环

Trace窗口显示Task 2 DONE

 

所以message log中的整体显示如下

 

 http://s11/middle/533d3f4f4bb07c6767c1a&690

 

 

 

Execution Graph中看起来会更直观一些http://s4/middle/533d3f4fhbb07d5facc43&690


在这个图中发现一个问题,显示TSK0~2每个任务都执行了六次,但是for循环中i只设置了五个值,这是因为在i=5时虽然跳出了for循环,但是继续执行下一条语句LOG_printf(&trace, "Task %d DONE", id);也就相当于i0加到5一共六个值,每个iTSK0~2都有执行,所以从05一共六次。

 

左上角还有个KNL_swi 是一个软中断,查看其属性如下图:http://s9/middle/533d3f4fhbb07d5fc9bf8&690

 

他的作用是中断访问TSK调度程序,程序一开始运行Other Thread,我想大概是一些初始化的线程,然后运行软中断KNL_swi使用户建立的任务都不执行,KNL-swi结束后才能开始执行TSK-Task Manager中用户建立的TSK0~2。当TSK0~2全部都结束后,KNL_swiOther Thread交替执行。

 

Execution Graph Details中的数据能看出TSK_idle  KNL_swi 管理用户任务的机制http://s7/middle/533d3f4fhbb07d5f95736&690

 

0

  

新浪BLOG意见反馈留言板 欢迎批评指正

新浪简介 | About Sina | 广告服务 | 联系我们 | 招聘信息 | 网站律师 | SINA English | 产品答疑

新浪公司 版权所有