2012年8月1日 星期三

INTEL HEX 格式

Intel HEX是一個文字檔,用來用來紀錄相對應的二進制碼。

格式:
:llaaaatt[dd...]cc
||||||||||||||||`` CHECKSUM (Zero checksum)
|||||||||```````- DATA
|||||||``- TYPE
|||||||     `- 00 : data record
|||||||     `- 01 : end of file record
|||||||     `- 02 : expended segment address record
|||||||     `- 04 : expended linear address record
|||````- ADDRESS
|``- LENGTH
`-START - colon

範例:

:10010000214601360121470136007EFE09D2190140
:100110002146017EB7C20001FF5F16002148011988
:10012000194E79234623965778239EDA3F01B2CAA7
:100130003F0156702B5E712B722B732146013421C7
:00000001FF



  Start code
  Byte count
  Address
  Record type
  Data
  Checksum




參考資料:
http://en.wikipedia.org/wiki/Intel_HEX
http://www.keil.com/support/docs/1584/

2012年7月26日 星期四

再論Linux開機

從電腦上電到出現命令提示符號間,系統經過了許多血汗的努力,這過程在使用者角度上不太重要,但,如果想要定做一個小型的Linux系統,就需要了解Linux整個啟動的過程。

當電腦上電之後首先是執行BIOS的程式,接著由BIOS交接到磁碟機上的MBR,通常OS Loader會載到MBR,這Loader負責把OS 核心(Kernel)與rootfs檔案initrd.img載入到記憶體中,並把控制權交接給核心運作,之後會解開initrd.img到記憶體上,成為暫時的rootfs但是是在RAM上,被稱為initrd (INITial Ram Disk),解開的rootfs之中有init這檔案,核心會去執行它,init(or linuxrc)必須要可以執行,可以是Script,有人稱它為Application Manager,這程式接手之後就得負責把磁碟機驅動起來,之後要掛載檔案系統,建立一些必要的設備節點,最後是根目錄切換,切換之後再去執行新的目錄中的init,把完整的系統驅動起來。

  1. bootloader載入kernel及initrd
  2. kernel解開initrd,並釋放initrd所佔用的記憶體空間
  3. 將rootfs掛載到ram disk上
  4. 執行 init (initialization)
  5. 掛載真正的rootfs
  6. chroot執行/sbin/init
所以第一次掛載ramfs時候如果需要開機到RAID上,就需要修改initrd.img這檔案,驅動起RAID並且掛載上再切換到RAID上,或是需要掛載iSCSI的磁碟當成系統碟也是需要修改它,如果不夠了解整個開機過程,相信沒辦法做到這一點,如果不需要太多的程序來搶資源,也可以讓自己寫的程式去領PID 1來用,整個系統就幾乎是你的程式獨占資源,所以對這些程序流程理解的愈深,相對的擁有的自由度就愈高。

當我在做小型的Linux系統的時候,我只需要開機到ramfs,所以不再往下交到目標磁碟機手上,而是直接用ramfs就好,一般這種作法搞出來的嵌入式系統是整個運作在記憶體上,好處是掛掉隨便使用者亂關都沒事,反正下一次要用還是得重新載入到記憶體上,只要原始的檔案沒毀損就沒事,缺點就是要等載入跟解壓縮,如此一來開機時間就會拉長,在很多的網通設備、多媒體播放器上都是這樣搞,只是他們也得面臨到開機速度的挑戰,所以就會看到各家奇奇怪怪的加速手段。

 在kernel版本2.6之後,initrd改用cpio製作,可以稱做cpio-initrd,它不需要特殊的block device或loop back device,製作過程比較簡單,而2.6與2.4的差異可以參考這一篇文章寫的。

上頭說的流程是Kernel 2.6以後的版本,而對於開機流程相信查到的文件常常是叫你去改inittab這檔案,如果你跟我一樣是用ubuntu/Debian就會發現事情並不單純(李組長語調),傳統的作法繼承於Unix-Like底下System-V init的作法,但是之後因為一堆隨身碟、硬碟、、、等隨插即用的東西出現,這個系統變得不太能夠適應,新的需求對於軟硬體的啟動、停止、掛載、移除,需要服務可以動態的啟動,傳統的sysVinit是基於runlevel的系統,使用runlevel(單、多使用者以及其它level)和鏈接(於/dec/rc?.d目錄,分別鏈接到/etc/init.d的init script)來啟動和關閉服務,而Ubuntu使用的是UPStart-Init則是基於事件的系統,它使用事件來啟動和關閉系統服務,傳統的SysVinit還有一個缺點,就是啟動需要跑一堆shell script,好處是很容易改,但是缺點是「慢」,這個缺點是從MacOS學到的教訓,在相同的位置上Solaris使用SMF(Service Management Facility),而Mac OS則使用Launchd,而Ubuntu則是傾向集這些軟體的優點於一身。

使用上也真的比較快,開機真的快多了,而且對於裝置服務的反應以比較靈敏,新的CPIO省去一次載入核心的時間,而init省去shell script運作產生的浪費,目前最耗時間的還是載入rootfs的時間(壓縮比加到頂也沒小多少,但是就明顯感覺核心解壓縮有點燒到點時間)。

sysVinit
  • initScript /rc script
  • rc => run commands
  • /etc/rc.d/init.d
  • /etc/inittab
    • id:5:initdefault:
  • /etc/rc.d/rc5.d
    • exp:
    • /etc/rc.d/rc5.d/K36mysqld
    • link to ../init.d/mysqld
    • K36mysqld
      • K : Kill/Start
      • 36: boot sequence
      • mysqld: service name
  • runlevel設定相互獨立
UPStart
  • event-driven/-based
  • 理順服務依賴關係以便實現平行啟動
  • 按需求啟動
  • Upstart job script
  • 有關UPStart相關的說明可以參考這一篇文章
也就是init最後不要交到真的磁碟機的/sbin/init而是交到ramfs裏面的/sbin/init,如果是用UPStart的服務,則是要搬相對的資料給他用,/etc/init目錄下的東西,底下的東西是.conf只是設定檔而已,不是shell script,而也要順便拷貝/etc/init.d目錄下的東西,除此之外還有相對應的設定檔也要拷貝,比如說ssh,除了init或init.d之外,還放了一個/etc/ssh/的目錄,也要順便拷貝走,與DNS相關的是/etc/hosts、/etc/resolv.conf、/etc/nsswitch.conf這3個設定檔,與帳號、密碼相關的設定檔是/etc/passwd、/etc/shadow、/etc/group這3個,如果說認証上有問題要注意/etc/pam.d/,PAM(Pluggable Authentication Modules),要順便注意/etc/nologin、/etc/securetty、/etc/security/*這堆。



2012年7月12日 星期四

我真的很懶嗎?


我一直覺得,我還蠻懶惰的,不喜歡做一堆重複的工作,寧願認真做完一次,寫個code,叫電腦自動做,也不願意重複的命令一直打,感覺這種行為很浪費生命,明明自動程序在跑幾秒鐘就沒事了,要燒個一天去做就感覺很白痴。

底下兩段CODE是把當下的UBUNTU或DEBIN系統抽出來做一個ROOTFS,也就是自動做出initrd.img的腳本,用Perl寫這種腳本還蠻快的,而且很好寫,主要是autofs.pl在運作,poCmd.pl是讀取cmd.list內容,讓autofs.pl去呼叫,poCmd.pl會按照cmd.list內列出來的命令,逐一拷貝到/bin底下,順便把需要的動態庫檔案也拷貝進去,後面要把busybox支援的命令在/bin底下做一個soft link,讓系統起來之後有一些基本的命令可以用。

原理就上一篇講的那些做一個自動腳本,把目前的系統抽一個initrd.img的小rootfs出來用,讓系統開機使用RAM DISK的ROOTFS運作,也就是有一些系統商做的小LINUX系統的搞法。

這種系統就是比誰做的小,也就是要做剛好的系統,這有兩個大原則,一個是只載入要用的模組,另外一個是只放需要的命令,所以不要白痴的把所有的模組都放在裏面,也不需要把沒用到的動態函式庫放進去,這樣會讓你做出來的ROOTFS會肥到百M的尺寸,要小,這就需要挑,挑的方法也很簡單,就先看目前系統需要哪些模組,lsmod這個命令可以列出目前系統載入了哪些模組,之後靠modinfo -n去看那個檔案放哪,只抓要用到的東西,另外有些命令用到動態庫,要調用ldd -v 命令去看用了哪些動態庫,只需要拷貝要用到的動態庫就好,這樣才能夠做出比較小的系統,我做出來的initrd.img大概就16M左右,事實上還好沒很肥,反正是自動做的,這大小還可以接受。

本來只是要我做個小系統,讓測試人員可以直接開進去使用,要穩、好拷貝,所以才要我搞這個,我也是努力的花了一星期(含其他案子同時進行)搞出來,下次就開腳本去抽就有了,不需要再來煩我~~XD。

當然不免俗的這程式有BUG(我知道有個問題),有看出來的可以留言,我們討論一下~~XD


poCmd.pl

#!/usr/bin/perl -w

open FH,"<../cmd.list";
foreach my $line(< FH >){
 chomp($line);
 if($line ne ""){
 my $limitCounter=0;
 DOAGAIN:
  my @paths=("/bin/","/sbin/","/usr/bin/","/usr/sbin/");
  print "$line";
  my $found=0;
  foreach my $path(@paths){
   if(-e "$path$line"){
    print "\t- $path$line\n";
    system "cp $path$line bin/.";
    my @vars=`ldd -v $path$line | grep lib | grep :\$ | cut -d ':' -f 1`;
    foreach my $var(@vars){
     chomp($var);
     $var =~ s/\t//g;
     $var =~ s/\ //g;
     print "\t$var\n";
     my $libPath="lib/.";
     #$libPath = "lib64/." if($var =~ /x86\_64/i);
     system "cp $var $libPath";
    }
    $found = 1;
    $limitCounter=0;
    last;
   }
  }
  if($found == 0){
   print "Can't found command exist!";
   system "sudo apt-get install $line";
   exit 1 if($limitCounter >= 3);
   $limitCounter++;
   goto DOAGAIN;
  }
 }
}

close FH;

#process busybox softlink

print "make busybox command list\n";
chdir "bin/";
my @vars = `busybox | grep \,\ `;
foreach my $var (@vars){
 if($var !~ /copyright/i){
  chomp($var);
  $var =~ s/\ //g;
  $var =~ s/\t//g;
  my @cmds = split /\,/,$var;
  foreach my $cmd(@cmds){
   if($cmd !~ /\[/){
    print "[busybox command]\t$cmd\n";
    system "ln -s busybox $cmd";
   }
  }
 }
}

autofs.pl

#!/usr/bin/perl -w

use File::Basename;
#Auto make rootfs on Debin/Ubuntu
#Author Jones
print "Auto make rootfs for Debin/Ubuntu\n";
print "Author Jones Lai\n";

my $var = `uname -a`;

if(($var !~ /ubuntu/i)&&($var !~ /debin/i)){
 print "This script just made for Debin/Ubuntu\n";
 exit 1;
}

$var = `dpkg -l`;

if($var !~ /build\-essential/){
 print "Require build-essential\r\n";
 system "sudo apt-get install build-essential";
}

my @kernels = `ls /lib/modules/`;

@kernels = sort {$b cmp $a} @kernels;

my $lastKernel = $kernels[0];

chomp($lastKernel);

print "Last kernel version is $lastKernel\n";

if(!(-e "vmlinuz")){
 print "copy kernel to local\n";
 system "cp /boot/vmlinuz-$lastKernel ./vmlinuz";
}
if(!(-e "initrd.img")){
 system "mkinitramfs -o initrd.img $lastKernel";
}
if(!(-e "tmp")){
 system "mkdir tmp";
}else{
 system "rm tmp/ -fr";
 system "mkdir tmp";
}

chdir "tmp/";
system "gunzip < ../initrd.img | cpio --extract --preserve --verbose --no-absolute-filenames";
my @modules = `lsmod`;

open(FH,">conf/modules");

foreach my $module(@modules){
 chomp($module);
 next if($module =~ /module/i);
 my ($MOD,$others) = split /\ +/,$module;
 print FH "$MOD\n";
 my $var = `modinfo -n $MOD`;
 chomp($var);
 my $dirname  = dirname($var);
 system "mkdir -p .$dirname/\n";
 system "cp -p $var .$var\n";
 print "[copy module]: $var\n";
}
close(FH);

system "perl ../poCmd.pl";

system "cp ../init init";
system "chmod +x init";

$var = `find . | cpio --create --format='newc' > ../newinitrd`;
print "$var\n";
$var = `gzip ../newinitrd`;
print "$var\n";
$var = `mv ../newinitrd.gz ../newinitrd.img`;
print "$var";
$var = `rm ../initrd.img` if(-e "../initrd.img");
$var = `mv ../newinitrd.img ../initrd.img`;

chdir "../";

2012年7月5日 星期四

運用ubuntu的initrd.img檔案作個小系統

syslinux


#dd if=/usr/lib/syslinux/mbr.bin of=/dev/sdx bs=512 count=1
#syslinux -sf /dev/sdx


syslinux.cfg
TIMEOUT 20
DEFAULT linux
LABEL linux
KERNEL vmlinuz
APPEND initrd=initrd.img
rootfs
直接叫ubuntu的工具做出來
mkinitramfs -o initrd.img /lib/modules/2.6.22-14-generic


1. 解開initrd.img
#cp initrd.img initrd.gz
#gunzip initrd.gz
#mkdir tmp2
#cd tmp2
#cpio -id --no-absolute-filenames < ../initrd

#cd tmp2
#gunzip < ../initrd.img | cpio --extract --preserve --verbose --no-absolute-filenames


2.壓縮initrd.img
#cp initrd.img initrd.img.org
#rm initrd.img
#cd workTemp
#find . | cpio --create --format='newc' > ../newinitrd
#gzip ../newinitrd
#mv ../newinitrd.gz ../newinitrd.img
#mv ../newinitrd.img ../initrd.img


修改init文件,主要是插入busybox的soft link,把命令指到busybox上

需要載入的核心模組修改conf/modules檔案。

拷貝命令到/bin底下,拷貝進去不見得就可以使用,還需要補足用到的動態函式庫,此時ldd命令就很重要。
比如說拷貝了perl命令

#ldd -v /usr/bin/perl

linux-gate.so.1 =>  (0x00d6b000)
libdl.so.2 => /lib/tls/i686/cmov/libdl.so.2 (0x00df2000)
libm.so.6 => /lib/tls/i686/cmov/libm.so.6 (0x003cf000)
libpthread.so.0 => /lib/tls/i686/cmov/libpthread.so.0 (0x008bf000)
libc.so.6 => /lib/tls/i686/cmov/libc.so.6 (0x001ad000)
libcrypt.so.1 => /lib/tls/i686/cmov/libcrypt.so.1 (0x00c14000)
/lib/ld-linux.so.2 (0x00e6c000)


Version information:
/usr/bin/perl:
libcrypt.so.1 (GLIBC_2.0) => /lib/tls/i686/cmov/libcrypt.so.1
libdl.so.2 (GLIBC_2.1) => /lib/tls/i686/cmov/libdl.so.2
libdl.so.2 (GLIBC_2.0) => /lib/tls/i686/cmov/libdl.so.2
libpthread.so.0 (GLIBC_2.2) => /lib/tls/i686/cmov/libpthread.so.0
libpthread.so.0 (GLIBC_2.0) => /lib/tls/i686/cmov/libpthread.so.0
libm.so.6 (GLIBC_2.0) => /lib/tls/i686/cmov/libm.so.6
libc.so.6 (GLIBC_2.4) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.3) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.3.4) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.1) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.3.2) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.11) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.2) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.1.2) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.0) => /lib/tls/i686/cmov/libc.so.6
/lib/tls/i686/cmov/libdl.so.2:
ld-linux.so.2 (GLIBC_PRIVATE) => /lib/ld-linux.so.2
libc.so.6 (GLIBC_2.1.3) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.1) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.0) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_PRIVATE) => /lib/tls/i686/cmov/libc.so.6
/lib/tls/i686/cmov/libm.so.6:
ld-linux.so.2 (GLIBC_PRIVATE) => /lib/ld-linux.so.2
libc.so.6 (GLIBC_2.1.3) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.0) => /lib/tls/i686/cmov/libc.so.6
/lib/tls/i686/cmov/libpthread.so.0:
ld-linux.so.2 (GLIBC_2.3) => /lib/ld-linux.so.2
ld-linux.so.2 (GLIBC_2.1) => /lib/ld-linux.so.2
ld-linux.so.2 (GLIBC_PRIVATE) => /lib/ld-linux.so.2
libc.so.6 (GLIBC_2.1.3) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.1) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.3.2) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.2) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_PRIVATE) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.0) => /lib/tls/i686/cmov/libc.so.6
/lib/tls/i686/cmov/libc.so.6:
ld-linux.so.2 (GLIBC_PRIVATE) => /lib/ld-linux.so.2
ld-linux.so.2 (GLIBC_2.3) => /lib/ld-linux.so.2
ld-linux.so.2 (GLIBC_2.1) => /lib/ld-linux.so.2
/lib/tls/i686/cmov/libcrypt.so.1:
libc.so.6 (GLIBC_2.1.3) => /lib/tls/i686/cmov/libc.so.6
libc.so.6 (GLIBC_2.0) => /lib/tls/i686/cmov/libc.so.6


函式庫還是要補上才可以使用,不然一執行就會出現錯誤訊息說有缺

2012年6月28日 星期四

保險佔了總收入的三分之一!!!

最近聽到同事生活吃緊,老是在哎哎叫,收入已經不夠優渥了,還讓保險吃掉總收入的三分之一,這讓我著實吃驚,感覺非常的...累人。

我想保險有幾個黃金原則:

  • 不能超過總收入的一成
    • 正如底下圖所顯示的一樣(引用來源)。
    • 試問當你都沒錢繳保費了,保障怎麼維持下去
    • 總不能不吃、不喝、不住吧
    • 所以當你保險費用已經佔了總收入的三分之一,是不是要剛好與投資理財對調呢?
    • 這樣理財的效率會不會太差一點,這兩種方法產生的財富我相信幾年之後會差很大,畢竟一年差了20%的投資金額,以最保守的定存來算也會差很多。


  • 會影響家計的成員最優先投保
    • 是有在工作的人失能對家計影響大,還是沒在工作的成員失能對家計影響大?
    • 當你選擇去保沒在工作的家庭成員時,難道不會影響到有在工作的成員的保險預算嗎?(如果你錢跟郭董一樣多,那幹嘛保險?)
    • 沒有扛家計責任的人湊熱鬧,在保什麼險?
    • 老婆沒在工作保費比較低,老公有在工作保費比較高,應該要替誰買保險?
    • 當然是老公阿!當有在工作的家庭成員失能時,你認為老婆的保費誰要繳?怎麼繳?難道拿保單去借錢來繳!?這不是本末倒置嗎?
    • 兒童壽險政府已經告訴你不能保,還是很多家長莫名其妙的想保,還來個保險最後限時搶購的戲碼,小孩又不是家中的經濟支柱,講句不好聽的實話,掛掉對你家計有什麼影響?莫名其妙,這些錢拿來保家長不是比較有價值嗎?
    • 家中的經濟支柱才需要保險,那是因為這個保險是為了防止意外,產生家中的經濟振盪,讓其他不事生產的成員產生突然而來的經濟壓力,而你保在這些成員身上,反而不去加碼在經濟支柱上,對家中的經濟穩定除了沒貢獻之外,還會造成更大的風險,當家中經濟支柱出現狀況時,其他成員反而要支付保險費,不是嗎?都沒在賺錢怎麼辦?此時保險公司還會來要你拿保單借錢,借不用還嗎?不是都是你的錢嗎?而且經濟結構都出現問題了,怎麼賺來還保險費?
    • 要我說,沒經濟產出的家庭成員,根本就不需要保險,風險高的經濟支柱,保險公司也不太想讓你保,風險高保費自然就高,這也本末倒置。
    • 你可以參考怪老子這一篇的文章,他觀念我還蠻認同的,而且還有EXCEL檔案帶算式可以精算一下。
  • 買保險不要想賺錢
    • 想想保險公司養那麼多業務、行政、肥貓不用錢嗎?
    • 那保險產生的利潤怎麼算?
    • 事實上可以看綠角的筆記,利率是保費定價的基礎之一,也就是說定存目前的利率會影響到你的保費,如果說定存利率愈高,相對的你的保費就愈低,反過來定存的利率愈低,相對的保費就愈高,為什麼?
    • 保險公司拿了錢放著不會生利息嗎?除了算死差益之外還是要賺利差益的部份阿,利差益就是保險公司預定的利率要低於定存阿,也就是你付出去錢有一部份的比例會押在定存上生利息,當然設計保單會依照利率來算計你的保費阿!不然怎麼賺錢?萬一賺的錢不夠支付支出時,難道要保險公司賠錢嗎?
    • 儲蓄險的利率不太可能高過定存利率,保險業務員會以總利率跟定存的年利率來比較,讓他家的儲蓄險看起來好像有點價值,但是一旦除以你投入時間就會發現,保單給的利息低的可憐,而且通常會比定存還要低,這很沒效率,所以買保險不要想賺錢!
    • 以我媽那張超爛的人情保單來說,躉繳(一次繳清)60萬,6年利率約是5%,5%看起來是比定存高,但是那是6年,定存利率指的是年利率,小時候老師有說不同單位不能來比較,沒忘的話拿起國小數學的除法來算,6年利率轉成年利率只需要除以6就好,這簡單阿!那就是0.8%嘛,這不只是低,還超低,而且低的可憐,而且還是單利,不像定存是複利在算,這就會差很大,以目前定存利率3年的利率1.4左右來算,大概是六十5萬兩千多元,而六年一次的單利則是六十三萬而已,也就是說,已經差了兩萬多,更不用說以前利率應該是2.2%左右,那應該是六十八萬四千多左右,這些錢到哪去了,當然是拿去給保險公司當規費去了,況且還有你的保險費要付,所以我可以說,大概是6年5萬多的差額給了保險公司,這不是在花錢嗎?所以買保險是在賺錢還是在賠錢?我對保障的內容更不滿意,保額根本沒多少。當真的經濟出現點問題的時候,那更慘,跟保險公司借錢?你的錢借出來還要付他們利息,解約還要付違約金,當初還是先扣掉規費才去算利息,也就是說我所謂的5%算出來的金額還高估了點,這合約真是爛透了。而且當你缺錢的時候要用,解約要按照年份賠錢,保單質借利息4.4%,而且是年利率複利喔,也就是說他在算目前的利率還是拿以前2.2%直接乘2喔,所以把錢拿去存保險公司是非常不划算的一件事情,比存定存還糟糕,而且簽下去就變成你欠他錢而且還是躉繳了狀態下也是欠保險公司錢。
    • 投資型保單也一樣,基金要帳戶保管費、外幣要手續費、、、等阿哩阿雜的費用要付掉,而且是先扣掉,後面才是拿去投資的,保險公司要的真是一毛都跑不掉,萬一跌破淨值呢?那是你的風險,對他們而言該扣還是要扣,他不會可憐你血本無歸的。
    • 所以保險不要想賺錢,那是在消費,那是在買商品,你面對的是保險「業務員」。

2012年6月20日 星期三

軟體外包印度真的有效率嗎?

底下這個code會讀取XLM的檔案,把內容透過PC的RS232 PORT傳送到LCM上,並且等著接收模組上按鍵回送的鍵盤碼,這程式只有40行還含註解,算是十分簡單的DEMO程式,可是測試LCM的DEMO程式要XML幹嘛阿?

這故事要說到印度阿三,東ㄠ西ㄠ的鬼叫LCM不會動,一下子懷疑電路有問題,一下子不會用Perl,搞得我火都上來了,就圖文並茂的必殺技開下去,後來乾脆把keypad的問題也搞定掉算了,就把原先的只會傳送資料出去的code改成收送都可以的版本,而讀XML就他X的奇怪,最好是跟我說他們軟體想要怎麼用,要去XML讀檔,拿到裏面的欄位阿,想要怎樣...怎樣啦!

挖賽~趕情是當成是在開軟體需求了勒!

我也真他X的仁慈,還幫他們把這XML功能寫上去(雖然對我沒難度,但是還是要哎一下),之前還說要改成我們的模組他們軟體要開發一個月(最好寫個小UI改IP要一個月啦),算了,以他們這種程度,真的沒幾個月搞不下來,他X的我就只有幾個小時可以搞,阿是怎麼樣。

軟體外包給印度搞真的有效率嗎?(可能只是因為這個客戶很病而已...其實人家印度還是很強的...話說現在隨便一隻手機都強過太空梭發射的時代...台灣還是沒發射火箭上去阿...)

#!/usr/bin/perl -w

use Device::SerialPort;
use XML::Simple;

$xml = new XML::Simple;

if(!(-f "data.xml")){
 print "Can't found XML file!\r\n";
 exit 1;
}

$data = $xml->XMLin("data.xml") or die "Can't open XML file!\r\n";

print "$data->{DATA}\r\n";

#Open port with parameter 9600n81
my $port = Device::SerialPort->new("/dev/ttyS0");
$port->databits(8);
$port->baudrate(9600);
$port->parity("none");
$port->stopbits(1);

#write data via serial port
#see LCD_COMMANDS.pdf page 1
#table for function/command
#0xF8 0x01 = Clear screen
#The following data will clear screen first then send your XML data

$displayStr = sprintf("%c%c",0xF8,0x01);
$port->write("$displayStr");
sleep(1);
$port->write("$data->{DATA}");

while(1){
 my ($count, $string) = $port->read(1);
 if($count > 0){
  print "Keycode = ".unpack("H*",$string)."\r\n";
 }
}

2012年6月19日 星期二

龜山工業區廠商名單

今天去工業局查一下龜山工業區的廠商名單,好當成找工作的參考依據,可惜那介面要按照種類去搜尋,使我非常不滿意,所以我希望能夠直接下載到名單,而不是在那裡操作個老半天,我發現他點進去各家廠商的資料是用網址欄的一個變數區分,這讓我有了想法,拿我那個超強的webTableKiller.pl的script來切切看,果不其然,效果超好的。

底下是列出來的名單:
公司名稱住址狀態產業類別
台達電子工業股份有限公司桃園市興隆路14號未建廠電腦、電子產品及光學製品製造業
杏隆實業股份有限公司桃園廠興隆路九號生產中紡織業
其洋股份有限公司興隆路八號生產中紙漿、紙及紙製品製造業
利華實業廠股份有限公司興隆路六之二號歇業紡織業
同良機械有限公司興隆路六之一號生產中機械設備製造業
名超企業股份有限公司桃園廠興隆路七號生產中塑膠製品製造業
源新織造廠有限公司桃園市興隆路6號停工紡織業
泰山電子股份有限公司興隆路四號生產中電腦、電子產品及光學製品製造業
昶維實業股份有限公司桃園縣桃園市興隆路三號生產中紡織業
杉信實業股份有限公司建國東路17號生產中塑膠製品製造業
三洋紡織纖維股份有限公司建國東路二四號生產中紡織業
三洋紡織纖維股份有限公司桃園二廠建國東路二六號生產中紡織業
振湧織造廠股份有限公司建國東路二八號生產中紡織業
昇頡實業股份有限公司建國東路34號2、3、4樓生產中紡織業
德星電子股份有限公司興隆路五號生產中電子零組件製造業
台灣富士全錄股份有限公司桃園縣桃園市興邦路四○號生產中電腦、電子產品及光學製品製造業
復盛應用科技股份有限公司一廠興中街9號生產中基本金屬製造業
友聯車材製造股份有限公司興中街一號生產中其他運輸工具製造業
萬坤股份有限公司興中街三號生產中紡織業
利百代國際實業股份有限公司桃園廠大誠路二號生產中其他製造業
利百代國際實業股份有限公司桃園二廠大誠路二之一號生產中基本金屬製造業
南亞食品工業股份有限公司桃園縣桃園市桃鶯路四一一號生產中食品製造業
恆新紡織(股)公司桃園市桃鶯路439號公告註銷紡織業
元隆汽車股份有限公司桃園市桃鶯路441號生產中汽車及其零件製造業
臺灣固特異股份有限公司桃園工廠桃鶯路四五一號歇業化學製品製造業
桃苗汽車股份有限公司桃園市桃鶯路445號生產中個人及家庭用品維修業
欣興機械工業有限公司大智路八號生產中金屬製品製造業
臺隆工業股份有限公司桃園工廠興華路一四號生產中食品製造業
嘉成建材工業股份有限公司興華路16號生產中金屬製品製造業
正裕特殊金屬股份有限公司興華路一九號生產中基本金屬製造業
來緯實業股份有限公司桃園市興華路10號停工
台灣表面黏著科技股份有限公司興華路七號生產中電腦、電子產品及光學製品製造業
緯聯企業股份有限公司興華路五號生產中紡織業
杉信實業股份有限公司二廠5鄰興華路3號生產中金屬製品製造業
新生銲條工業股份有限公司大智路11號1樓生產中金屬製品製造業
龍膳坊企業有限公司龜山廠桃園縣龜山鄉山鶯路163之1號生產中食品製造業
榮恆興業有限公司興邦路41號生產中機械設備製造業
英屬維京群島商太古可口可樂股份有限公司台灣分公司桃園廠興邦路46號生產中飲料製造業
上展金屬工業股份有限公司桃園廠桃園縣桃園市興邦路三九號生產中金屬製品製造業
大宇紡織股份有限公司桃園一廠興邦路四二號生產中紡織業
欣興電子股份有限公司興邦廠興邦路38號歇業電子零組件製造業
南僑化學工業股份有限公司桃園廠興邦路35號生產中食品製造業
台灣富士全錄股份有限公司第二廠興邦路三六號生產中電腦、電子產品及光學製品製造業
友霖生技醫藥股份有限公司桃園製藥廠大誠路11號生產中藥品製造業
美達工業股份有限公司山頂村興邦路三一號生產中金屬製品製造業
仁美織造有限公司桃園縣龜山鄉龜山工業區建國東路四○號生產中紡織業
台灣獅王化工股份有限公司桃園工廠山鶯路一六○號歇業
台灣富貴電子工業股份有限公司山鶯路一五八號生產中電子零組件製造業
新將軍股份有限公司桃園廠山鶯路一五六之二號一樓生產中電腦、電子產品及光學製品製造業
佳世達科技股份有限公司桃園廠山鶯路157號生產中印刷及資料儲存媒體複製業
正洸股份有限公司桃園廠山鶯路198之2、198之4號生產中成衣及服飾品製造業
美德耐股份有限公司桃園縣龜山鄉山頂村興業街2號生產中
和碩聯合科技股份有限公司桃園廠興業街5號、5號2樓之1(第三層)、5號7樓之1、5號8樓之1生產中電子零組件製造業
理隆纖維工業(股)公司桃園廠龜山鄉興業街9號1樓歇業紡織業
東方石材股份有限公司桃園縣龜山鄉山福村頂興路六○號歇業
裕器工業股份有限公司桃園廠山鶯路一六三號歇業
台達電子工業股份有限公司桃園二廠山鶯路252號1樓及3至10樓生產中電子零組件製造業
旺機針織有限公司桃園廠中興路1之1號1樓生產中紡織業
中誠企業股份有限公司中興路二號生產中紡織業
力儂企業股份有限公司山鶯路二九○號生產中紡織業
廣大飼料(股)公司桃園廠龜山鄉山鶯路169號歇業食品製造業
兆豐國際商業銀行龜山倉庫龜山鄉山鶯路344號生產中其他製造業
富祐鴻科技股份有限公司山鶯路350號生產中電腦、電子產品及光學製品製造業
香榮實業股份有限公司山鶯路國光巷一號生產中紡織業
福大化學工業股份有限公司山鶯路國光巷三號生產中化學製品製造業
欣興電子股份有限公司精密載板事業部三廠山鶯路173-1、173-2、171-2、173-8號生產中電子零組件製造業
台灣立凱電能科技股份有限公司桃園縣桃園市大林里興華路2-1號生產中
晟峰精密工業股份有限公司山鶯路中華巷2之1號(1、2樓)、2之1號3樓生產中塑膠製品製造業
啟利實業股份有限公司山鶯路文華巷2號生產中紡織業
瑞怡造漆有限公司桃園廠山鶯路171-1、171-5號生產中化學製品製造業
佳世達科技股份有限公司雙星廠山鶯路159號1、5、7樓生產中電子零組件製造業
綠德富股份有限公司大智路6、6之1號生產中電子零組件製造業
高菖企業股份有限公司建國東路19號生產中化學材料製造業
旭慶光電股份有限公司山鶯路國光巷6號生產中機械設備製造業
科嶠工業股份有限公司桃園廠桃園縣龜山鄉山頂村山鶯路華玉巷3號生產中機械設備製造業
山福工業股份有限公司桃園縣龜山鄉龜山工業區興邦路33號生產中機械設備製造業
利樂科技股份有限公司大林里大誠路六號歇業橡膠製品製造業
臺灣華歌爾股份有限公司二廠興邦路二七、二九號生產中成衣及服飾品製造業
來佳針織廠股份有限公司桃園廠建國東路二五號一樓歇業成衣及服飾品製造業
凱崴電子股份有限公司桃園廠興邦路32號1、2、3樓生產中金屬製品製造業
桃園汽車客運股份有限公司修車廠興中街五號生產中汽車及其零件製造業
四維精密材料股份有限公司桃園廠興華路12號生產中紙漿、紙及紙製品製造業
中國電器股份有限公司桃園廠興華路一八號生產中電力設備製造業
臺灣華歌爾股份有限公司一廠興邦路二九之一號生產中紡織業
上展金屬工業股份有限公司桃園二廠興邦路37之1號生產中基本金屬製造業
台灣電力股份有限公司龜山鄉興邦路37號電力設備製造業
全廣食品有限公司桃園廠大誠路四號一樓生產中食品製造業
謹成工業股份有限公司桃園廠大智路九號生產中電子零組件製造業
銓銘金屬工業股份有限公司龜山廠山頂村山鶯路三五八號生產中基本金屬製造業
星大精密股份有限公司興華路6號1樓生產中金屬製品製造業
台達電子工業股份有限公司桃園廠興邦路三一之一號生產中電子零組件製造業
新立汽車有限公司桃園縣桃園市大林里大誠路3號生產中個人及家庭用品維修業
興磊科技股份有限公司興中街2號生產中金屬製品製造業
隆億服裝材料廠股份有限公司興業路三一號生產中紡織業
東正元電路工業股份有限公司桃園廠桃園縣桃園市大誠路10號歇業電子零組件製造業
棋傑企業有限公司桃園廠大豐路4號生產中金屬製品製造業
宜美不銹鋼工業有限公司桃園縣桃園市桃鶯路445之1號1樓生產中家具製造業
金永興科技股份有限公司大誠路7號2樓生產中機械設備製造業
福翁工業股份有限公司桃園廠大智路一○號生產中汽車及其零件製造業
裝宏企業有限公司桃園廠興華路1號3樓生產中化學製品製造業
復盛應用科技股份有限公司三廠興華路一之二號生產中金屬製品製造業
裕隆汽車製造股份有限公司工程中心試造工廠桃園縣桃園市興邦路四五之二號生產中汽車及其零件製造業
翊聖企業股份有限公司興邦路三三之一號生產中塑膠製品製造業
鍵銓精密工業有限公司頂興路六四巷一號歇業
欣興電子股份有限公司精密載板事業部一廠山鶯路175-1號生產中電子零組件製造業
勵精股份有限公司桃園工廠興華路二號歇業紡織業
和益貿易股份有限公司龜山廠山鶯路一五六之五號生產中紙漿、紙及紙製品製造業
摩托迪克股份有限公司桃園廠興業街二七號二、三樓生產中電力設備製造業
益茂國際有限公司頂興路六四巷三號生產中紡織業
達方電子股份有限公司精機廠山鶯路167號生產中塑膠製品製造業
協隆針織廠頂興路六四巷五號歇業
良器有限公司建國東路32之1號1、2、3樓生產中塑膠製品製造業
名檠科技股份有限公司興邦路39之11號歇業塑膠製品製造業
龍億精密工業股份有限公司興邦路39之9號生產中金屬製品製造業
泳達精密科技股份有限公司龜山廠興邦路39-5號生產中電腦、電子產品及光學製品製造業
上展金屬工業股份有限公司桃園市大林里興邦路39之3號生產中金屬製品製造業
台灣科萊恩化學股份有限公司桃園化工廠興邦路3○號生產中化學製品製造業
萬錩實業有限公司頂興路六四巷八號生產中塑膠製品製造業
元大電子股份有限公司桃園廠山鶯路三四○巷一號生產中電腦、電子產品及光學製品製造業
憶全企業股份有限公司山鶯路三四○巷八號生產中電腦、電子產品及光學製品製造業
立昌先進科技股份有限公司龜山廠山鶯路三四0巷六號生產中電子零組件製造業
佳豪實業股份有限公司興邦路三九之六號生產中紡織業
中榮彈簧股份有限公司山鶯路三四0號生產中金屬製品製造業
毅昌精密工業有限公司桃園縣龜山鄉山福村頂興路六四巷九號一樓生產中機械設備製造業
台錦工業廠有限公司二廠桃園縣龜山鄉山福村頂興路六四巷七號生產中塑膠製品製造業
佳總興業股份有限公司興邦路39之2、39之4號生產中電子零組件製造業
維倫紡織股份有限公司山鶯路340巷2號生產中紡織業
信東生技股份有限公司祐益廠桃鶯路445之2號2樓生產中化學製品製造業
綿春纖維工業股份有限公司桃園廠興業街一三號生產中紡織業
底下是把龜山工業區廠商名單全部印出來的code。
#!/usr/bin/perl -w

for$i (1..999){
 $url=sprintf("http://www.moeaidb.gov.tw/iphw/gueishan/factory.do?method=goContent&fn=%04d-00&unitId=0511012",$i);
 #print "$url\r\n";
 $ret=`perl webTableKiller.pl big5 \"$url\" 龜山工業區廠商資料.csv`;
 if($ret ne ""){
  print "$ret\r\n";
 }
}