Design Pattern-Dispatcher

看完 RUN!PC 六月號由李維先生所寫的”由軟體品質檢驗談Design Pattern的應用”一文,我覺得用 VFP 就可以很簡單的作到,所以就以 VFP 實作.
該文以計算牌照稅為引子
計算牌照稅的時候,會需要依照汽缸的cc數以及私人/營業用車來判定收費的標準,照一般的寫法,很自然就會用到很多 If…Then…Else 或 do case…endcase, 可是這樣子程式碼就會變得很長很長,而難以維護.
像是這樣:
If cc < 500
  money=900
else
  if cc < 600
    money=1200
    &&….. 略
  endif
endif
用 do case 的話則是這樣
do case
  case between( 0, 500 )
    money=900
  case between( 501, 599 )
    money=1200
  && … 略
endcase
李先生以一個 Dispatcher pattern 解決此一問題.
在 VFP 裡面可以直接結合資料庫作更好的解法
*
* ITax.prg
*
DEFINE CLASS ITax as custom
  PROCEDURE Init()
    create cursor crTax( cc_lo I, cc_hi I, PrivateTax Y, BusinesTax Y )
    insert into crTax values ( 0, 500, $ 1620, $ 900 )
    insert into crTax values ( 501, 599, $ 2160, $ 1200 )
    insert into crTax values ( 600, 1199, $ 4320, $ 2160 )
    insert into crTax values ( 1200, 1799, $ 7120, $ 3060 )
    insert into crTax values ( 1800, 2399, $11230, $ 6480 )
    insert into crTax values ( 2400, 2999, $15210, $ 9900 )
    insert into crTax values ( 3000, 4199, $28220, $16380 )
    insert into crTax values ( 4200, 5399, $46170, $24300 )
    insert into crTax values ( 5400, 6599, $69690, $33660 )
    insert into crTax values ( 6600, 7799, $117000, $44460 )
    insert into crTax values ( 7800, 9999999, $117000, $44460 )
  ENDPROC
  PROCEDURE Destroy()
    use in crTax
  ENDPROC
  PROCEDURE GetTax( cc, theKind )
    local ly_result
    local lc_oldalias
    lc_oldalias=alias()
    select("crTax")
    go top
    locate for between( cc, crTax.cc_lo, crTax.cc_hi )
    if found()
      ly_result=crTax.&theKind
    else
      ly_result=0
    endif
    select( lc_oldalias )
    return ly_result
  ENDPROC
  PROCEDURE GetPrivateTax( cc )
    return this.GetTax( cc, "PrivateTax" )
  ENDPROC
  PROCEDURE GetBusinessTax( cc )
    return this.GetTax( cc, "BusinesTax" )
  ENDPROC
ENDDEFINE
*
* test_itax.prg
*
LOCAL lo_obj
set procedure to itax.prg
lo_obj=createobject("ITax")
? lo_obj.GetPrivateTax( 1000 )
? lo_obj.GetBusinessTax( 2000 )
瞧,這樣不是簡單多了嗎??
在這裡拋磚引玉一下,希望大家如果有更好的解法
也 post 上來,讓大家觀摩一下
^_^

讓你的 Apache 支援 SSL

Linux 版本 Red Hat 7.3
安裝:
確定有安裝 openssl 與 mod_ssl 相關套件.
步驟:
請切換到 /etc/httpd/conf 下
輸入 make server.crt
依照指示輸入答案後,目錄下應會產生 server.crt 與 server.key 兩個檔案
將 server.key 放到 ssl.key/ 下
將 server.crt 放到 ssl.crt/ 下
編輯 httpd.conf
作如下修改:
SSLCertificateFile /etc/httpd.conf/ssl.crt/server.crt
SSLCertificateKeyFile /etc/httpd.conf/ssl.key/server.key
重新啟動 httpd ,應該就可以了~
這樣子產生的認證在使用上,瀏覽器會提出警告,告知這個憑證並非放在一個具公信力的地方,容易造成使用者困擾.
因此仍要向具公信力的機構申請才是.
目前產生的認證,期限是一年,你可以編輯 Makefile ,找尋 -days 365
將其改為你所需要的天數即可.
若不使用 mod_ssl 提供的 Makefile
你也可以手動使用 openssl 指令來產生
步驟如下:
– 產生 .key (public)
openssl genrsa -des3 -out ca.key 1024
– 驗證 .key
openssl rsa -noout -text -in ca.key
– 產生 .crt (public)
openssl req -new -x509 -days 365 -key ca.key -out ca.crt
– 驗證 .crt
openssl x509 -noout -in ca.crt
– 產生 .key (private)
openssl genrsa -des3 -out server.key 1024
– 驗證 .key
openssl rsa -noout -text -in server.key
– 產生 .csr
openssl req -new -key server.key -out server.csr
– 查看 .csr
openssl req -noout -text -in server.csr
– 產生 .crt
一種是使用 sign.sh, 它會依據 server.csr 來產生 server.crt , 但我怎麼找都找不到 sign.sh
以下是看 Makefile 而得來的
openssl req -new -key server.key -x509 -days 3650 -out server.crt
資料參考: 永遠的UNIX論壇 (http://www.fanqiang.com/)

mp4player trace 筆記

mp4player 是 mpeg4ip 內附的一個 player
RFC 1889 RTP 被 RFC 3550 淘汰(obsolete)
video 繼承 video_sdl
– 由 player_session 建立之,用以 sync video/audio
– 主要由 player_media 使用,player_session貫穿主軸,在建立video和player_media實體時,都會把自己傳入.
player_media 建立 plugin 時,會把 video_sync(m_video_sync)傳入codec_plugin中.
各個 codec_plugin 為 xxxx_file.cpp
codec_plugin 利用 check_for_video_codec() 傳回之.
plugin實作檔案最後都有一個 macro 定出 structure: mpeg4ip_codec_plugin.
如此一來,codec_plugin_cpp的 check_for_video_codec()/check_for_audio_codec() 即可利用 dlsym() 找到它,並依據此 structure 去叫用 plugin 中的 function.
rtsp_thread()
+-> get_rtp_packet()
 +-> callback_for_rtp_packet()
  +-> 呼叫設置的 callback
在 rtsp_thread 中,作完 callback 後,會呼叫 periodic(), 這也是藉由 rtsp_thread_set_rtp_callback() 去設置的.
c_rtp_periodic(), 用 rtsp_thread_set_rtp_callback()設進去.
mp4player 中,callback function (CPlayerMedia::rtp_receive_packet(),此 function 會被包在 c_rtp_packet_callback, 再被上面的 rtsp_thread_set_rtp_callback() 設進去)
判斷 interleaved 而決定呼叫 rtp_process_recv_data() 或 rtp_process_ctrol().
periodic function 則呼叫 rtp_byte_stream() 去 recv_task (在 rtp_bytestream.cpp )
上面的那個段落又會呼叫 rtp_update(), rtp_update() 收 packet, 呼叫 callback.
rtp_update()(or callback??) 會執行 timeout_rr(), 而 timeout_rr() 中會執行 rtp_init_extern_net().
指定的 callback: c_recv_callback() => player_media->recv_callback() => stream->recv_callback() 放在 queue 中.
systems.h
– include necessary headers and redefine data types.
sdp.h
– session description protocol
rtsp_private.h
– the major rtsp interface
sdl.h
-> needed, for thread-control (create, mutex…and so on)
rtsp_create_client_for_rtp_tcp()
– create mutex
– create thread, 同時亦建立 unix socket, 之後的 function 會透過此 socket 與 thread 溝通, thread 主體在 rtsp_thread.c (rtsp_thread())中.
圖片及相關檔案:

Continue reading “mp4player trace 筆記”

lvm – simple usage

須將 partition type 設為 0x8e
pvcreate /dev/hdxn 初始化 lvm partition
vgcreate 建立 volume group
lvcreate 向 volume group 索取 logical volume
之後就可以去 format, 或 mount 或做些你要做的事情啦
lvremove 則是移除 logical volume
vgremove 則是移除 volume group
變更大小或屬性時,則使用 XXextend, XXchange….