91视频免费?看_蜜芽MY188精品TV在线观看_国产免费无遮挡在线观看视频_深夜国产_亚洲精品欧洲精品_欧美黑人粗暴多交

  • 回復
  • 收藏
  • 點贊
  • 分享
  • 發新帖

談談關于復雜性多任務程序的原理和設計程序

當你看到操作系統的多任務并行的時候,你是否覺的很神奇呢?你是否想過那些任務的時間片輪轉是怎么實現的呢?這個時間片輪轉的秘密是什么呢?相信很多單片機初學者都會對這個問題感興趣。

當你查看單片機的匯編指令的時候,你是否留意過中斷返回指令的操作過程?如果你留意過這個操作過程的話,你一定會發現它通過堆棧復原PC指針的過程。也就是說:當單片機產生中斷的時候,它會把當前程序正在運行的PC指針保存在堆棧當中;然后當中斷程序運行完畢的時候,程序執行中斷返回指令,把堆棧中保存的PC指針再返回出來。

這個是單片機運行的正常情況,但是如果在單片機的中斷中修改了堆棧中的PC指針值,那么是不是中斷就返不回來原來的程序地址?如果還是這個地址是我故意設定的值那么他是不是執行完這個中斷就跳到我的設定的這個地址上去了?

如果這個地址又是另外一個任務的地址的時候不是正好實現了從一個任務的死循環中跳到了另外一個任務的死循環中去了?對了!沒錯!多任務并行運行、時間片輪轉的秘密就是:在定時中斷中修改堆棧,使保存在中斷中PC指針按照預定的方式改變從而讓PC指針在幾個任務地址中不停的跳轉。

如果你有空去看UCOS的移植代碼的時候,你會發現切換任務的asm函數就是在修改堆棧的內容。當然了,真正的任務的切換過程不僅僅是修改PC指針的堆棧內容,同時也修改了單片機所用到的所有可能被用到的寄存器的內容。

全部回復(15)
正序查看
倒序查看
001a
LV.3
2
2014-02-11 16:30

分享的是我寫的一個雙任務并行的程序。一個任務是“main”函數的死循環,另外一個任務是函數“task1”中的死循環。任務操作很簡單,就是兩個io口不停在切換電平,但是由于兩個任務中的時間延時不一樣而是切換電平的頻率不一樣。單片機用的是瑞薩k0s系列的單片機(應為這個是我工作中常用的型號,我現在對這個比較熟,而51單片機很久沒有用過了,所以用的是這個型號,什么時候有空了我再寫個51單片機的程序)。有這個系列單片機開發板的可以單步運行看看任務切換過程中“偷換”堆棧內容的過程。(后面將分享我在這個平臺下寫的一個簡單的時間片輪轉的小操作系統)修改堆棧內容的中斷函數:

__interrupt void MD_INTTM80( void )

{

/* TODO */

#asm

push ax

push bc

push de

push hl

movw ax,sp

movw bc,ax

mov a,#0ffh

sub a, c

inc a

mov c,a ;the sp_long

;/*********************;load the sp_long*****************************/

mov a,c

mov !0fec0h,a ;load the sp_long

;/**************************************************/

mov b,a ;load the data

movw de,#0feffh

movw hl,#0fec1h

?L_mov1: mov a,[de]

mov [hl],a

decw de

dec b

incw hl

mov a,b

cmp a,#0h

bnz $?L_mov1

;/************************load the data to sp**************************/

mov a,!0fea0h ;load the data to sp

mov b,a

movw de,#0fea1h

movw hl,#0feffh

?L_mov2: mov a,[de]

mov [hl],a

incw de

dec b

decw hl

mov a,b

cmp a,#0h

bnz $?L_mov2

;/*************************get the new sp_point*************************/

mov a,#0ffh ;get the new sp_point

sub a,!0fea0h

inc a

mov !0fe90h,a

mov a,#0feh

mov !0fe91h,a

;/************************save the sp_data**************************/

mov a,!0fec0h ;save the sp_data

mov !0fea0h,a

mov b,a

movw de,#0fec1h

movw hl,#0fea1h

?L_mov_sp: mov a,[de]

mov [hl],a

incw de

dec b

incw hl

mov a,b

cmp a,#0h

bnz $?L_mov_sp

#endasm

/**************************************************/

#asm

mov a,!0fe90h

mov x,a

mov a,!0fe91h

movw sp,ax

pop hl

pop de

pop bc

pop ax

#endasm

}

 

附上原理圖,之后咱們再談談如何設計復雜的多任務程序

程序和原理圖:

AVR-多任務模擬系統設計(程序 原理圖).rar

 

0
回復
matou
LV.3
3
2014-02-22 20:08
@001a
分享的是我寫的一個雙任務并行的程序。一個任務是“main”函數的死循環,另外一個任務是函數“task1”中的死循環。任務操作很簡單,就是兩個io口不停在切換電平,但是由于兩個任務中的時間延時不一樣而是切換電平的頻率不一樣。單片機用的是瑞薩k0s系列的單片機(應為這個是我工作中常用的型號,我現在對這個比較熟,而51單片機很久沒有用過了,所以用的是這個型號,什么時候有空了我再寫個51單片機的程序)。有這個系列單片機開發板的可以單步運行看看任務切換過程中“偷換”堆棧內容的過程。(后面將分享我在這個平臺下寫的一個簡單的時間片輪轉的小操作系統)修改堆棧內容的中斷函數:__interruptvoidMD_INTTM80(void){/*TODO*/#asmpushaxpushbcpushdepushhlmovwax,spmovwbc,axmova,#0ffhsuba,cincamovc,a;thesp_long;/*********************;loadthesp_long*****************************/mova,cmov!0fec0h,a;loadthesp_long;/**************************************************/movb,a;loadthedatamovwde,#0feffhmovwhl,#0fec1h?L_mov1:mova,[de]mov[hl],adecwdedecbincwhlmova,bcmpa,#0hbnz$?L_mov1;/************************loadthedatatosp**************************/mova,!0fea0h;loadthedatatospmovb,amovwde,#0fea1hmovwhl,#0feffh?L_mov2:mova,[de]mov[hl],aincwdedecbdecwhlmova,bcmpa,#0hbnz$?L_mov2;/*************************getthenewsp_point*************************/mova,#0ffh;getthenewsp_pointsuba,!0fea0hincamov!0fe90h,amova,#0fehmov!0fe91h,a;/************************savethesp_data**************************/mova,!0fec0h;savethesp_datamov!0fea0h,amovb,amovwde,#0fec1hmovwhl,#0fea1h?L_mov_sp:mova,[de]mov[hl],aincwdedecbincwhlmova,bcmpa,#0hbnz$?L_mov_sp#endasm/**************************************************/#asmmova,!0fe90hmovx,amova,!0fe91hmovwsp,axpophlpopdepopbcpopax#endasm} 附上原理圖,之后咱們再談談如何設計復雜的多任務程序[圖片]程序和原理圖:AVR-多任務模擬系統設計(程序原理圖).rar 
這個想法不錯,實現起來不知道難不難,能不能用c語言實現
0
回復
daylight
LV.4
4
2014-02-22 20:09
@001a
分享的是我寫的一個雙任務并行的程序。一個任務是“main”函數的死循環,另外一個任務是函數“task1”中的死循環。任務操作很簡單,就是兩個io口不停在切換電平,但是由于兩個任務中的時間延時不一樣而是切換電平的頻率不一樣。單片機用的是瑞薩k0s系列的單片機(應為這個是我工作中常用的型號,我現在對這個比較熟,而51單片機很久沒有用過了,所以用的是這個型號,什么時候有空了我再寫個51單片機的程序)。有這個系列單片機開發板的可以單步運行看看任務切換過程中“偷換”堆棧內容的過程。(后面將分享我在這個平臺下寫的一個簡單的時間片輪轉的小操作系統)修改堆棧內容的中斷函數:__interruptvoidMD_INTTM80(void){/*TODO*/#asmpushaxpushbcpushdepushhlmovwax,spmovwbc,axmova,#0ffhsuba,cincamovc,a;thesp_long;/*********************;loadthesp_long*****************************/mova,cmov!0fec0h,a;loadthesp_long;/**************************************************/movb,a;loadthedatamovwde,#0feffhmovwhl,#0fec1h?L_mov1:mova,[de]mov[hl],adecwdedecbincwhlmova,bcmpa,#0hbnz$?L_mov1;/************************loadthedatatosp**************************/mova,!0fea0h;loadthedatatospmovb,amovwde,#0fea1hmovwhl,#0feffh?L_mov2:mova,[de]mov[hl],aincwdedecbdecwhlmova,bcmpa,#0hbnz$?L_mov2;/*************************getthenewsp_point*************************/mova,#0ffh;getthenewsp_pointsuba,!0fea0hincamov!0fe90h,amova,#0fehmov!0fe91h,a;/************************savethesp_data**************************/mova,!0fec0h;savethesp_datamov!0fea0h,amovb,amovwde,#0fec1hmovwhl,#0fea1h?L_mov_sp:mova,[de]mov[hl],aincwdedecbincwhlmova,bcmpa,#0hbnz$?L_mov_sp#endasm/**************************************************/#asmmova,!0fe90hmovx,amova,!0fe91hmovwsp,axpophlpopdepopbcpopax#endasm} 附上原理圖,之后咱們再談談如何設計復雜的多任務程序[圖片]程序和原理圖:AVR-多任務模擬系統設計(程序原理圖).rar 
單片機小型操作系統多任務并行的原理,不錯
0
回復
001a
LV.3
5
2014-02-22 20:11
@001a
分享的是我寫的一個雙任務并行的程序。一個任務是“main”函數的死循環,另外一個任務是函數“task1”中的死循環。任務操作很簡單,就是兩個io口不停在切換電平,但是由于兩個任務中的時間延時不一樣而是切換電平的頻率不一樣。單片機用的是瑞薩k0s系列的單片機(應為這個是我工作中常用的型號,我現在對這個比較熟,而51單片機很久沒有用過了,所以用的是這個型號,什么時候有空了我再寫個51單片機的程序)。有這個系列單片機開發板的可以單步運行看看任務切換過程中“偷換”堆棧內容的過程。(后面將分享我在這個平臺下寫的一個簡單的時間片輪轉的小操作系統)修改堆棧內容的中斷函數:__interruptvoidMD_INTTM80(void){/*TODO*/#asmpushaxpushbcpushdepushhlmovwax,spmovwbc,axmova,#0ffhsuba,cincamovc,a;thesp_long;/*********************;loadthesp_long*****************************/mova,cmov!0fec0h,a;loadthesp_long;/**************************************************/movb,a;loadthedatamovwde,#0feffhmovwhl,#0fec1h?L_mov1:mova,[de]mov[hl],adecwdedecbincwhlmova,bcmpa,#0hbnz$?L_mov1;/************************loadthedatatosp**************************/mova,!0fea0h;loadthedatatospmovb,amovwde,#0fea1hmovwhl,#0feffh?L_mov2:mova,[de]mov[hl],aincwdedecbdecwhlmova,bcmpa,#0hbnz$?L_mov2;/*************************getthenewsp_point*************************/mova,#0ffh;getthenewsp_pointsuba,!0fea0hincamov!0fe90h,amova,#0fehmov!0fe91h,a;/************************savethesp_data**************************/mova,!0fec0h;savethesp_datamov!0fea0h,amovb,amovwde,#0fec1hmovwhl,#0fea1h?L_mov_sp:mova,[de]mov[hl],aincwdedecbincwhlmova,bcmpa,#0hbnz$?L_mov_sp#endasm/**************************************************/#asmmova,!0fe90hmovx,amova,!0fe91hmovwsp,axpophlpopdepopbcpopax#endasm} 附上原理圖,之后咱們再談談如何設計復雜的多任務程序[圖片]程序和原理圖:AVR-多任務模擬系統設計(程序原理圖).rar 

寫自己的小型單片機操作系統代碼解析三:__interrupt void MD_INTTM80( void ) 解析:這用的C語言中嵌入匯編語言的方式寫的匯編語言。實現的功能是我放第一貼講的任務切換的匯編語言是一樣的。簡單說一下這里匯編實現的功能:

1、調用函數 stick_chang_task(void)獲取當前任務堆棧的初始地址和下個任務堆棧的初始地址。

2、保存此時單片機中的堆棧內容到當前運行的任務的中的任務堆棧

3、把下一個任務中的任務堆棧數組的內容覆蓋到單片機的堆棧中

4、根據下一個任務堆棧數組中的內容恢復SP的值

0
回復
001a
LV.3
6
2014-02-22 20:11
@001a
寫自己的小型單片機操作系統代碼解析三:__interruptvoidMD_INTTM80(void)解析:這用的C語言中嵌入匯編語言的方式寫的匯編語言。實現的功能是我放第一貼講的任務切換的匯編語言是一樣的。簡單說一下這里匯編實現的功能:1、調用函數stick_chang_task(void)獲取當前任務堆棧的初始地址和下個任務堆棧的初始地址。2、保存此時單片機中的堆棧內容到當前運行的任務的中的任務堆棧3、把下一個任務中的任務堆棧數組的內容覆蓋到單片機的堆棧中4、根據下一個任務堆棧數組中的內容恢復SP的值

自己的小型單片機操作系統代碼解析二:

void cread_task(void(*task)(void),unsigned char *stack_) 解析

這個函數的作用是:建立死循環的任務。

參數:

task

任務函數。建立死循環任務的時候,任務的函數名,用來獲取任務的函數名。

stack_

任務堆棧的數組指針。

os_sub_tasknum++;// 任務總數加1

ostask_stask_adress[(os_sub_tasknum-1)]=(unsigned int)stack_;//把當前任務 用的任務堆棧地址首地址,賦值到這個數組給任務調度分配的時候用,也就是當前時間片運行完后,決定運行那一個任務的時候就靠他了。

int_task(task,stack_);//初始化任務堆棧

void stick_chang_task(void) 解析

這個函數在 “時間中斷函數”__interrupt void MD_INTTM80( void ) 中調用。用來實現任務調度的功能。在里,任務可以按照時間片一個個進行循環運行就是靠這個函數實現的。

old_task=ostask_stask_adress[os_cur_tasknum];//當前運行的任務堆棧首地址賦值給全局變量old_task

os_cur_tasknum++;//當前第幾個任務

if(os_cur_tasknum>=os_sub_tasknum)

{

os_cur_tasknum=0;

}

new_task=ostask_stask_adress[os_cur_tasknum];//下一個要運行的任務堆棧首地址賦值給全局變量new_task

//判斷是否是第一次任務切換時候用到。第一次任務切換的時候是從main中切換出來的,不需要保存當前的的堆棧內容,所以設這個值給“時間中斷函數”__interrupt void MD_INTTM80( void ) 切換任務的時候進行判斷

os_1st_time++;

if(os_1st_time>1)

{

os_1st_time=2;

}

0
回復
001a
LV.3
7
2014-02-22 20:13
@001a
自己的小型單片機操作系統代碼解析二:voidcread_task(void(*task)(void),unsignedchar*stack_)解析這個函數的作用是:建立死循環的任務。參數:task任務函數。建立死循環任務的時候,任務的函數名,用來獲取任務的函數名。stack_任務堆棧的數組指針。os_sub_tasknum++;//任務總數加1ostask_stask_adress[(os_sub_tasknum-1)]=(unsignedint)stack_;//把當前任務用的任務堆棧地址首地址,賦值到這個數組給任務調度分配的時候用,也就是當前時間片運行完后,決定運行那一個任務的時候就靠他了。int_task(task,stack_);//初始化任務堆棧voidstick_chang_task(void)解析這個函數在“時間中斷函數”__interruptvoidMD_INTTM80(void)中調用。用來實現任務調度的功能。在里,任務可以按照時間片一個個進行循環運行就是靠這個函數實現的。old_task=ostask_stask_adress[os_cur_tasknum];//當前運行的任務堆棧首地址賦值給全局變量old_taskos_cur_tasknum++;//當前第幾個任務if(os_cur_tasknum>=os_sub_tasknum){os_cur_tasknum=0;}new_task=ostask_stask_adress[os_cur_tasknum];//下一個要運行的任務堆棧首地址賦值給全局變量new_task//判斷是否是第一次任務切換時候用到。第一次任務切換的時候是從main中切換出來的,不需要保存當前的的堆棧內容,所以設這個值給“時間中斷函數”__interruptvoidMD_INTTM80(void)切換任務的時候進行判斷os_1st_time++;if(os_1st_time>1){os_1st_time=2;}

寫自己的小型單片機操作系統代碼解析一

:我寫的這個小型操作系統核心代碼在工程的“mini_os”目錄下。從今天開始將陸續對mini_os.c文件的函數進行解析。里面總共4個函數,分別是:

void cread_task(void(*task)(void),unsigned char *stack_);

void int_task(void(*task)(void),unsigned char *stack_);

void stick_chang_task(void);

__interrupt void MD_INTTM80( void );

他們分別實現的功能是:建立任務API函數;初始化任務函數,在建立任務函數中掉用;實現任務調度順序的函數;實現任務切換的核心代碼,是匯編語言寫的。void int_task(void(*task)(void),unsigned char *stack_);

解析:可能很多人看著個函數都覺的很奇怪,為啥全是賦值?操作系統說白是用代碼虛擬一個CPU出來,那么你想想,一個CPU要想運行是不是需要自己的基本數據空間呢?那就對了。這個作為一個任務的初始化函數,那肯定得給一個任務虛擬一段這任務的數據空間了。這一段數據通常被稱為任務堆棧。所以任務建立的時候每一個任務都要建立自己的一個數組所為任務堆棧,不同的任務是不能共用同一個數組作為任務堆棧的。這個數據結構包括:數據的長度(兩個字節)、PSW、任務函數的地址、通用寄存器的。這個結構的順序并不是固定的,但是要和任務切換函數里寫的要一致。

0
回復
close3
LV.5
8
2014-02-22 20:15
混合編程,多謝分享
0
回復
001a
LV.3
9
2014-02-22 20:17
@001a
分享的是我寫的一個雙任務并行的程序。一個任務是“main”函數的死循環,另外一個任務是函數“task1”中的死循環。任務操作很簡單,就是兩個io口不停在切換電平,但是由于兩個任務中的時間延時不一樣而是切換電平的頻率不一樣。單片機用的是瑞薩k0s系列的單片機(應為這個是我工作中常用的型號,我現在對這個比較熟,而51單片機很久沒有用過了,所以用的是這個型號,什么時候有空了我再寫個51單片機的程序)。有這個系列單片機開發板的可以單步運行看看任務切換過程中“偷換”堆棧內容的過程。(后面將分享我在這個平臺下寫的一個簡單的時間片輪轉的小操作系統)修改堆棧內容的中斷函數:__interruptvoidMD_INTTM80(void){/*TODO*/#asmpushaxpushbcpushdepushhlmovwax,spmovwbc,axmova,#0ffhsuba,cincamovc,a;thesp_long;/*********************;loadthesp_long*****************************/mova,cmov!0fec0h,a;loadthesp_long;/**************************************************/movb,a;loadthedatamovwde,#0feffhmovwhl,#0fec1h?L_mov1:mova,[de]mov[hl],adecwdedecbincwhlmova,bcmpa,#0hbnz$?L_mov1;/************************loadthedatatosp**************************/mova,!0fea0h;loadthedatatospmovb,amovwde,#0fea1hmovwhl,#0feffh?L_mov2:mova,[de]mov[hl],aincwdedecbdecwhlmova,bcmpa,#0hbnz$?L_mov2;/*************************getthenewsp_point*************************/mova,#0ffh;getthenewsp_pointsuba,!0fea0hincamov!0fe90h,amova,#0fehmov!0fe91h,a;/************************savethesp_data**************************/mova,!0fec0h;savethesp_datamov!0fea0h,amovb,amovwde,#0fec1hmovwhl,#0fea1h?L_mov_sp:mova,[de]mov[hl],aincwdedecbincwhlmova,bcmpa,#0hbnz$?L_mov_sp#endasm/**************************************************/#asmmova,!0fe90hmovx,amova,!0fe91hmovwsp,axpophlpopdepopbcpopax#endasm} 附上原理圖,之后咱們再談談如何設計復雜的多任務程序[圖片]程序和原理圖:AVR-多任務模擬系統設計(程序原理圖).rar 
補充下,任務切換是不分優先級的
0
回復
001a
LV.3
10
2014-02-22 20:20

今天公開我的之前寫的仿UCOS(只有多任務切換的功能,是我發的第一個貼的程序的升級版),任務建立的多少跟ram的空間大小有關,平臺MCU:NEC 公司的(現在為瑞薩公司)k0s系列9234,開發環境PM+。

任務調用程序一覽:

void task1(void);//任務1函數聲明

void task2(void);/任務2函數聲明

void task3(void);/任務3函數聲明

unsigned char task1_stask[30],task2_stask[30],task3_stask[30];//任務堆棧用到的數據空間

void delay(unsigned int i)

{

while(i--);

}

unsigned int ii1,ii2;

unsigned char a1;

int j;

void main( void )

{

/* TODO. add user code */

static unsigned int j,i;

ii1=0;

ii2=0;

PM3.3=0;

PM3.2=0;

PM4.2=0;

//inti_task_sp();

#asm

mov a,#0feh

mov x,#0ffh

movw sp,ax

#endasm

//初始化SP指針

cread_task(task1, task1_stask);

cread_task(task2, task2_stask);

cread_task(task3, task3_stask);

//建立三個任務

TM80_Start();

//開始任務調度

while(1);

}

void task1(void)//任務1內容

{

static unsigned int i;

i=1;

stask_:

while(1)

{

//ii2++;

//i=50000;

P3.2=~P3.2;

delay(20000);

//while(i--);

}

ii2++;

ii2++;

ii2++;

goto stask_;

}

void task2(void)//任務2內容

{

main_:

while(1){

//ii1++;

//j=300;

P3.3=~P3.3;

delay(1000);

//while(j--);

//j=10000;

//while(j--);

//i=10000;

//while(i--);

//i=10000;

//while(i--);

}

//ii1++;

//ii1++;

//ii1++;

goto main_;

}

void task3(void)//任務3內容

{

main_:

while(1){

//ii1++;

//j=300;

P4.2=~P4.2;

delay(4000);

//while(j--);

//j=10000;

//while(j--);

//i=10000;

//while(i--);

//i=10000;

//while(i--);

}

//ii1++;

//ii1++;

//ii1++;

goto main_;

}

caozuoxintong_v3.1.zip

0
回復
for_real
LV.3
11
2014-02-22 20:22
@001a
今天公開我的之前寫的仿UCOS(只有多任務切換的功能,是我發的第一個貼的程序的升級版),任務建立的多少跟ram的空間大小有關,平臺MCU:NEC公司的(現在為瑞薩公司)k0s系列9234,開發環境PM+。任務調用程序一覽:voidtask1(void);//任務1函數聲明voidtask2(void);/任務2函數聲明voidtask3(void);/任務3函數聲明unsignedchartask1_stask[30],task2_stask[30],task3_stask[30];//任務堆棧用到的數據空間voiddelay(unsignedinti){while(i--);}unsignedintii1,ii2;unsignedchara1;intj;voidmain(void){/*TODO.addusercode*/staticunsignedintj,i;ii1=0;ii2=0;PM3.3=0;PM3.2=0;PM4.2=0;//inti_task_sp();#asmmova,#0fehmovx,#0ffhmovwsp,ax#endasm//初始化SP指針cread_task(task1,task1_stask);cread_task(task2,task2_stask);cread_task(task3,task3_stask);//建立三個任務TM80_Start();//開始任務調度while(1);}voidtask1(void)//任務1內容{staticunsignedinti;i=1;stask_:while(1){//ii2++;//i=50000;P3.2=~P3.2;delay(20000);//while(i--);}ii2++;ii2++;ii2++;gotostask_;}voidtask2(void)//任務2內容{main_:while(1){//ii1++;//j=300;P3.3=~P3.3;delay(1000);//while(j--);//j=10000;//while(j--);//i=10000;//while(i--);//i=10000;//while(i--);}//ii1++;//ii1++;//ii1++;gotomain_;}voidtask3(void)//任務3內容{main_:while(1){//ii1++;//j=300;P4.2=~P4.2;delay(4000);//while(j--);//j=10000;//while(j--);//i=10000;//while(i--);//i=10000;//while(i--);}//ii1++;//ii1++;//ii1++;gotomain_;}caozuoxintong_v3.1.zip
看匯編,就象看天書啊
0
回復
soap泡泡
LV.4
12
2014-02-22 20:23
C語言也有時間片輪轉啊。網上一搜大把的。
0
回復
elio
LV.2
13
2014-02-22 20:24
加上調度機制,這其實就是就是所有操作系統最基礎的東西。
0
回復
vidas
LV.2
14
2014-02-22 20:25
@for_real
看匯編,就象看天書啊
看不懂匯編,但是好多的底層必須用匯編,真糾結呀,,,好比對SP,PC的更改,對堆棧的更改
0
回復
candyman
LV.2
15
2014-02-22 20:27
有C語言的嗎?
0
回復
001a
LV.3
16
2014-02-22 20:28
@candyman
有C語言的嗎?

木有啊。。。C語言不能獲取堆棧SP當前的值,這樣獲取不了堆棧長度(當前堆棧長度=當前堆棧的值和原來設的堆棧底之差的絕對值)。       

上面匯編的內容是:先保護常用寄存器 ax bc de hl(如果是51單片那么對應的應該是r0 r1 r2 r3 ...) ;然后計算堆棧長度;再把堆棧數據全部復制到一段數據“1”區內(這個是數據去起中間緩存的作用),并且保存這段數據的長度;再把數據“2”區內的數據覆蓋回原來的堆棧(數據“2”區就是上一個任務的堆棧數據);再根據數據“2”去的數據長度回復SP值;再把數據“1”區的數據覆蓋數據“2”去的數據(下個中斷來的時候再把這個數據“2”區的書覆蓋堆棧);最后還原常用寄存器 ax bc de hl 數據,退出中斷(因為我寫的匯編是嵌在C語言中的,所以不用這個匯編指令)。

0
回復
主站蜘蛛池模板: 同江市| 玛沁县| 镇平县| 慈溪市| 日喀则市| 古蔺县| 沛县| 新乡市| 香港 | 醴陵市| 龙门县| 灵丘县| 广水市| 来安县| 美姑县| 鄯善县| 耒阳市| 铜山县| 南昌市| 运城市| 孟津县| 巢湖市| 广南县| 诸城市| 巴林右旗| 和政县| 镇江市| 成武县| 沙河市| 永仁县| 北川| 临洮县| 旬邑县| 久治县| 吉首市| 固镇县| 泰兴市| 驻马店市| 黑山县| 大渡口区| 斗六市|