1. 問題描述
用dz60的計時器測週期時發現,tpm(計時器)在初始化後,需要等待500多ms才能勉強測到。
tpm產生的波形如下圖,藍色波形上公升沿為初始化指令執行完成時間點,用乙個io口輸出高電平並延時100ms作為示波器觸發源,黃色波形為tpm的pwm方式輸出波形。
2. 問題分析
在dz60datasheet中文版第313頁找到這段話。
大概意思是tpm的通道控制暫存器的更新時機由clksb:clksa控制。而clksb:clksa的功能如表16-3所示。
合起來就是說,對通道控制暫存器的寫入,不是直接寫到暫存器裡面,而是先寫到暫存器對應的緩衝器。當tpm計數器關閉時,寫入的資料從緩衝器寫入完成後立即更新到暫存器;而當tpm有時鐘在執行時,寫入的資料更新則需要等到,計時器從0xfffe變成0xffff才開始進行。
由此想到,產生問題的tpm初始化是128分頻(16mhz匯流排時鐘下,週期為8us)。16位tpm計數器從0開始計數,則有更新設定需等待時間為65535×8us=524ms。與所見波形符合。
3. 問題解決
無論tpm用作輸入捕捉,還是pwm或者比較輸出,所有tpm控制暫存器初始化時,都要先把時鐘關掉,即clksb:clksa=0b00。問題解決後得到波形如下:
4. 正確例項
//初始化時必須先關掉時鐘,否則以下兩個暫存器要到將要溢位即(0xfffe->0xffff)時才會更新。
//--如果設定128分頻,則初始化時間需要 16mhz/128*65535=524ms
//關掉時鐘初始化,則暫存器在寫入完成後立即更新,無需等待。
//tpm2產生**對齊pwm輸出
tpm_cstr(tpm_num_2) =0b00100111;
// |||||||
// ||||||+-----ps0\
// |||||+------ps1 ----128倍分頻
// ||||+-------ps2/
// |||+--------clksa\
// ||+---------clksb/--關時鐘
// |+----------cpwms---所有通道以**對齊pwm模式執行
// +-----------toie----禁止溢位中斷
//tpm1設定為輸入捕捉
tpm_cstr(tpm_num_1) =0b00000111;
// |||||||
// ||||||+-----ps0\
// |||||+------ps1 ----128倍分頻
// ||||+-------ps2/
// |||+--------clksa\
// ||+---------clksb/--關時鐘
// |+----------cpwms---所有通道以輸入捕捉執行
// +-----------toie----禁止溢位中斷
//tpm2通道設定
tpm2_chscstr(tpm_chno)=0b00101000;
// |||||
// ||||+-----elsa\
// |||+------elsb/---high-true 脈衝(清除向上比較輸出)
// ||+-------msa\
// |+--------msb/----cpwms=1時,此設定無效
// +---------chie----禁止中斷
tmp = period * (125) / 2;
tpm2mod = tmp; //週期period以ms為單位
tpm2c0v = tmp / 10 * duty / 10; //占空比duty為0~100整數
tpm2sc_clksb = 0;
tpm2sc_clksa = 1; //暫存器設定完成,再開啟匯流排時鐘,避免長時間的暫存器更新。
//tpm2通道設定
tpm1sc_clksb = 0;
tpm1sc_clksa = 1; //暫存器設定完成,再開啟匯流排時鐘,避免長時間的暫存器更新。
tpm1sc_toie = 1; //使能輸入捕捉中斷
enabletpm1chint(g_tmuch_start);
中斷程式的寫法如下
interrupt void isrt1ch0in(void)
//暫存器設定完成,再開啟匯流排時鐘,避免長時間的暫存器更新。
tpm1sc_clksb = 0;
tpm1sc_clksa = 1;
tpm1sc_toie = 1;
enabletpm1chint(g_tmuch_stop);
break;
case 1:
//第二次觸發,儲存資料
g_stop_data = tpm1c0v;
g_trigged++;
//時間採集完畢,恢復成io功能
tpm1_chscstr(g_tmuch_start)=0b00000000;
tpm1_chscstr(g_tmuch_stop)=0b00000000; //恢復成io功能
break;
default:
break;} }
enableinterrupt(); //開放總中斷
}
微控制器實現60s定時器
微控制器573 數碼管 按鈕 實現60秒的定時器 知識 ie暫存器 tcon暫存器 tmod 暫存器 2個定時中斷,2個按鈕中斷 include define seg p2 數碼管 斷碼口 define scanp p1 數碼管 com掃瞄口 sbit oc p0 0 定義573鎖存器使能口,我是用...
微控制器定時器雙擊 微控制器實現60s定時器
2個定時中斷,2個按鈕中斷 include define seg p2 數碼管 斷碼口 define scanp p1 數碼管 com掃瞄口sbit oc p0 0 定義573鎖存器使能口,我是用的573驅動7段數碼管 sbit pb0 p3 2 按鈕0 sbit pb1 p3 3 按鈕1 第乙個定...
STC12C5A60S2 51微控制器最小系統
stc12c5a60s2 一.根據晶元文件連線物理電路,最小系統 如果裝置未識別,需要安裝usb驅動 2.安裝keil編譯器 1 新建乙個工程,再新建乙個原始碼檔案,再把檔案新增到專案中去 新建project project new project 填寫專案名稱 點選儲存 選擇晶元型號 atmel ...