2013年5月22日 星期三
如何產生任意大小的磁碟影像
也是Bee第一次在MCU上使用到64位元整數變數。
這種變數數值太大想都沒想過。但遇到檔案系統位址索引就非用不可。
FatFs可以在PC上進行模擬,會產生一個Ram Disk。
不過這個Ram Disk沒有和真實世界相通。
是可以載入SD卡影像檔,但抓取費時。
本想用其他Ram Disk的影像檔來用。結果沒想到Windows有內建。
就在控制台->系統管理工具->電腦管理->磁碟管理
可以在硬碟上產生一個新的碟。
設定上要使用固定大小,不然無法對應真實磁碟。
可以格式化,放入檔案。操作完畢後中斷連接。
再來就可以用檔案讀入的方式Copy進Ram中,給FatFs做為Disk影像用。
2013年5月12日 星期日
從CPU公司併購看科技之發展
Bee一向後知後覺:
Intel賣掉ARM核心一年後才知。
MIPS被Imagination Technologies併購半年才知。
這二件事時代不同,看似無關,卻是電腦科技的重要分叉路。
Intel賣掉ARM核心,Bee當時認為是不合理的事,ARM核是發展PDA的核心,Intel擺明要失去PDA市場。過了幾年,結果更慘,PDA和手機完全合體後,ARM處理器已經成為主流CPU之一。
至於MIPS被併,則可以見得,GPU的重要性已經和CPU不相上下。
那就電腦科技來說,路又是如何走的。
CPU一開始因需求計算力,在達到有效需求的運算力之前,其他功能皆不是重點。Intel在計算力的推展符合需求,造就了帝國企業。
當CPU發展到64位元時,就出現了應用需求減緩,正代表已達到基本需求運算力。再來就會有其他問題出現,此時PDA興起,代表能量效率的需求,ARM因此發展成霸主。就目前來看,x86指令解碼電路至少是ARM的三倍,長期下去x86絶非對手。
GPU公司併購CPU公司,代表CPU已無新公司生存空間,也代表GPU已開始和CPU平起平坐。
GPU是如何和CPU能平起平坐,一般人應是無法理解。其實在生物上已經發現相同的問題,解法也是一樣,同時使用。
生物解決自然界問題,和科技是相同的。應是說工程問題相同,只是解決材料不同。在生物從單一感測細胞進展到多重感測細胞,最終發展出視覺細胞,就開始遇到計算問題。邏輯運算和影像運算無法使用同一種單元來做,應說是同是腦細胞,但二者所需的連結結構不同,無法同時存在。於是大腦就分成二個腦,一個做為邏輯運算而另一個做為影像運算。發展了上億年,二個大腦還是沒有因為是那一個重要,而有特別去發展。有的是同時變大。
電腦科技已經開始走入邏輯運算和影像運算並行發展的年代,但因影像運算較為後起,所以市場空間尚未佔足,還有可以成長的空間。而CPU核心設計的市場則是過了高原期,接下來的發展會比以前慢得多。不信的人,您可以看看,若是您買了一台新PC(或NB)您說得出CPU多了什麼功能嗎?就是因為連CPU公司也說不出來,才會多了一堆型號(就這裏多一點,那裏少一點),完全沒有創新的內容。就算有創新,也不是客戶關心的內容。
2013年4月23日 星期二
FatFs使用修改
FatFs可以動作:讀取檔案、寫出檔案皆有執行。
但寫出檔案的日期有問題,因為沒有RTC故無時間資料。
時間資料可以給一個固定值,但固定值由人來填寫不太有利。
利用C語言中的__TIME__及__DATE__來做為時間常數。
__TIME__的格式為”hh:mm:ss”
是固定的ASCII碼,所以轉成數值無問題。
__DATE__的格式為”Mmm dd yy”
dd yy也是ASCII也無問題。
Mmm為三個英文字,要轉成1~12變得很麻煩。
三個英文字要分成12個月,只要判定後二字就可以分。
只好寫一個switch case去做12個月字母去分類。
最後將__TIME__及__DATE__用const字串去存。
設定有最佳化的Compiler設定後,可以看到反組譯的結果為:
\ get_fattime:
\ 00000000 0x.... LDR.N R0,??DataTable7_4 ;; 0x42938746
\ 00000002 0x4770 BX LR ;; return
結果只有二個指令,只回傳定值。
寫了近90行程式,只會編成二個指令,就是4個Byte。
測試寫入檔案的時間是對的,會是編譯的時間。
程式碼:
#define DC(t,a,b) (((a)<<8)+(b))
unsigned char const Date[] = __DATE__;
unsigned char const Time[] = __TIME__;
DWORD get_fattime (void)
{
BYTE rtcYear , rtcMon , rtcMday, rtcHour, rtcMin, rtcSec;
DWORD time;
#ifdef USE_FS_RTC
RTC_TimeTypeDef RTC_TimeStructure;
RTC_DateTypeDef RTC_DateStructure;
/* Get info from RTC here */
RTC_GetTime(RTC_Format_BIN, &RTC_TimeStructure);
rtcSec = RTC_TimeStructure.RTC_Seconds;
rtcMin = RTC_TimeStructure.RTC_Minutes;
rtcHour = RTC_TimeStructure.RTC_Hours;
RTC_GetDate(RTC_Format_BIN, &RTC_DateStructure);
rtcYear = RTC_DateStructure.RTC_Year;
rtcMon = RTC_DateStructure.RTC_Month;
rtcMday = RTC_DateStructure.RTC_Date;
#else
rtcSec = ((Time[6]-'0')*10+(Time[7]-'0'));
rtcMin = ((Time[3]-'0')*10+(Time[4]-'0'));
rtcHour = ((Time[0]-'0')*10+(Time[1]-'0'));
rtcYear = ((Date[9]-'0')*10+(Date[10]-'0')+20);
rtcMday = (Date[4]==' ')? (Date[5]-'0'): ((Date[4]-'0')*10+(Date[5]-'0'));
switch ((Date[1]<<8)+Date[2])
{
case DC('J','a','n') :
rtcMon = 1;
break;
case DC('F','e','b') :
rtcMon = 2;
break;
case DC('M','a','r') :
rtcMon = 3;
break;
case DC('A','p','r') :
rtcMon = 4;
break;
case DC('M','a','y') :
rtcMon = 5;
break;
case DC('J','u','n') :
rtcMon = 6;
break;
case DC('J','u','l') :
rtcMon = 7;
break;
case DC('A','u','g') :
rtcMon = 8;
break;
case DC('S','e','p') :
rtcMon = 9;
break;
case DC('O','c','t') :
rtcMon = 10;
break;
case DC('N','o','v') :
rtcMon = 11;
break;
case DC('D','e','c') :
rtcMon = 12;
break;
default :
rtcMon = 1;
break;
}
#endif
/* Pack date and time into a DWORD variable */
time = (((DWORD)rtcYear) << 25)
| ((DWORD)rtcMon << 21)
| ((DWORD)rtcMday << 16)
| (WORD)(rtcHour << 11)
| (WORD)(rtcMin << 5)
| (WORD)(rtcSec >> 1);
return time;
}
2013年3月19日 星期二
CPU市場鐵律:量變引發質變
意思是當某種型式CPU在市場上佔有數量優勢時,就會形成絶對性優勢。
這和CPU本身品質無關,只因硬體相容性可以讓軟體好好發展。
而要佔有數量,價格不用說一定要夠低,另一種是開放性,非獨家生產。
PC市場因壟斷較看不出來,但MCU卻是很明顯。
8051是8位元MCU的霸主,因為大家都可以做硬體。
16位元來不及有霸主就直接進入32位元MCU時代。
而32位元MCU的霸主正在形成。
硬體統一完畢,再來會變成軟體開始統一。
結果也會有類似的現象,會有統一的軟體架構出現。
又走"量變引發質變"這條路,軟體架構的品質不是重點,而是使用量。
不管軟硬體,使用者習慣才是主導,而市場往使用者多的方向走。
2013年3月16日 星期六
Cortex M4推展不如預期
主因是,要浮點運算做什麼?
往8位元MCU轉來的工程師,對於能在32位元上開發程式已是很開心,要玩的一堆,還沒有意識到浮點運算要如何用,那又何必多花錢。
而從PC轉來的工程師對於CM4的執行效能根本看不上眼,去玩Cortex-A8還比較實在,因為Cortex-A8也不貴。
這樣的局面造成CM4不上不下的樣子。
還有各廠商自行發展的32位元處理器,其實Bee也不太看好。
現在市場已經轉成由軟體來主導,要換MCU談何容易。連軟體工具都要換新,那來那個時間。
至少CM3還可以降為CM0或升級為CM4,光是這樣就可以吃很久,那還有機會看別的MCU。
萬一有什麼大的應用,轉到Cortex-A8也是不差的選擇。
MCU現在只是一個骨架系統,再來需求會轉往拼裝系統的速度。
再來就要看工程師如何快速拼裝系統,拼裝快硬體價格低才是重點。
2013年3月14日 星期四
簡單多工於Cortex-M3上最佳化
原程式:
void main(void)
{
InitSystem();
INIT_DEVICE();
while (1)
{
switch (Task_State[FuncID])
{
case TASK_RUNNING :
TaskFunc[FuncID]();
break;
case TASK_SKIP :
if ( Task_Delay_Count[FuncID] )
{
Task_Delay_Count[FuncID]--;
if (! Task_Delay_Count[FuncID]) WakeUp(FuncID);
}
break;
default:
break;
}
if ( ++FuncID >= TASK_NUM ) FuncID = 0;
}
}
新程式:
void main(void)
{
InitSystem();
INIT_DEVICE();
while (1)
{
register unsigned int temp_id;
register unsigned int temp_delay;
temp_id = FuncID;
switch (Task_State[temp_id])
{
case TASK_RUNNING :
TaskFunc[temp_id]();
break;
case TASK_SKIP :
temp_delay = Task_Delay_Count[temp_id];
if ( temp_delay )
{
temp_delay--;
Task_Delay_Count[temp_id] = temp_delay;
if (! temp_delay) WakeUp(temp_id);
}
break;
default:
break;
}
if ( ++temp_id >= TASK_NUM ) temp_id = 0;
FuncID = temp_id;
}
}
因核心程式執行未檢討有無可以改善空間,因此段程式決定各工作間的掃描率,若是可以改善將增加工作效率。
分析原本的程式,發現有多一些記憶體存取動作。
於是將記憶體動作簡化,中間使用暫存器的方式應可以加速。
先將FuncID這個變數用暫存器變數取出,編出來的程式少了一個指令。
又將Task_Delay_Count[]也用暫存器變數,有少一點組合語言指令。
主要廻圈原需要16個指令,現在只剩下12個指令,少了四個指令。
原16個指令需要23個Clock執行時間,現在12個指令只要19個Clock執行時間。
用示波器實測,Skip 1000次需時5.02ms,原先為6.80ms,確實加速執行時間。
不過Cortex M3用暫存器變數直接使用int會比short及char來得有效率。中間會少了正負號擴張指令,所以速度會更快。
2013年3月6日 星期三
Cortex-M4開啟新MCU戰場
CM3因為ST已是獨大,所以各廠商就將重心移往CM4。
直到最近TI推展CM4時,才發現價格已經壓到US$3以下。
有浮點運算器的MCU是這樣的價格,等於ADC/DAC不用什麼錢。
其他可以用於浮點運算的應用可以普及。
這樣的轉變,離上次Bee認為32位元MCU變革,只過了剛好一年。
32位元浮點運算,已不是8位元MCU可以做的事。
再下來會大量使用的演算法如:
矩陣運算、傅利葉轉換等等,都會變成非常容易達成。
這樣子MCU程式和PC程式之間差異就更小了。
看來只剩作業系統相容度的問題了。
另一個是使用浮點運算時,可能有效能不足需稍長的時間。
使用作業系統將長時間運算程式做為低優先權的運算,這樣的應用會增多。
RTOS因CM4的出現將會推展的更快。