13.04.2015 Views

東海大學資訊工程與科學系畢業專題成果競賽 - 東海大學‧資訊工程學系

東海大學資訊工程與科學系畢業專題成果競賽 - 東海大學‧資訊工程學系

東海大學資訊工程與科學系畢業專題成果競賽 - 東海大學‧資訊工程學系

SHOW MORE
SHOW LESS

You also want an ePaper? Increase the reach of your titles

YUMPU automatically turns print PDFs into web optimized ePapers that Google loves.

東 海 大 學 資 訊 工 程 與 科 學 系<br />

畢 業 專 題 成 果 競 賽<br />

< Zigbee 定 位 與 智 慧 型 行 動 購 物 導 覽 應 用 ><br />

專 題 實 驗 報 告 書<br />

指 導 教 授 : 石 志 雄<br />

專 題 組 員 :963849 謝 佳 峻<br />

中 華 民 國 九 十 九 年 十 二 月 十 八 日<br />

1


目 次<br />

一 、 摘 要 ……………………………………………………………………………3<br />

二 、 前 言 與 文 獻 回 顧 ………………………………………………………………4<br />

三 、 設 計 原 理 分 析 …………………………………………………………………5<br />

3-1. 伺 服 器 接 收 RSSI 產 生 定 位 資 訊 的 方 式 …………………………………5<br />

3-2. 伺 服 端 與 客 戶 端 …………………………………………………………7<br />

3-3. 裝 置 與 主 機 的 通 訊 方 式 …………………………………………………8<br />

3-4. 伺 服 端 與 客 戶 端 的 通 訊 方 式 ……………………………………………9<br />

3-5. 客 戶 端 顯 示 的 相 關 資 訊 …………………………………………………10<br />

3-6. 確 認 圖 形 介 面 的 運 作 正 常 ………………………………………………10<br />

3-7. 最 短 路 徑 的 表 示 …………………………………………………………11<br />

四 、 軟 硬 體 系 統 說 明 ………………………………………………………………12<br />

五 、 團 隊 分 工 合 作 方 式 ……………………………………………………………15<br />

六 、 成 果 與 討 論 ……………………………………………………………………15<br />

七 、 結 論 ……………………………………………………………………………20<br />

八 、 參 考 文 獻 ………………………………………………………………………20<br />

九 、 附 錄 ……………………………………………………………………………21<br />

2


一 、 摘 要<br />

ZigBee 是 一 種 新 的 短 距 離 無 線 通 訊 標 準 , 具 有 統 一 感 測 器 、 致 動 器 、 設 備 、 資 產 追<br />

蹤 設 備 的 資 料 通 訊 方 法 的 可 能 。 它 利 用 電 池 供 電 設 備 的 低 資 料 率 和 低 負 載 週 期 , 提 供<br />

構 建 可 靠 但 成 本 可 承 受 的 網 路 骨 幹 , 可 以 用 在 很 多 應 用 中 , 如 工 業 自 動 化 、 公 用 事 業<br />

計 量 、 大 樓 控 制 甚 至 是 玩 具 。ZigBee 協 定 目 前 的 版 本 採 用 IEEE802.15.4 短 距 離 無 線 通 訊<br />

標 準 , 而 上 層 網 路 層 和 應 用 支 援 層 則 透 過 ZigBeeAlliance 來 制 定 , 應 用 層 則 有 一 Profile<br />

來 規 範 , 由 於 低 成 本 、 低 耗 電 的 優 勢 , 使 得 ZigBee 在 國 內 外 市 場 的 接 收 度 與 普 及 率<br />

日 漸 提 高 , 根 據 Siemens 的 RokeManorResearch 分 析 , ZigBee 應 用 會 在 家 庭 建 築 物 自<br />

動 化 、 個 人 感 測 網 路 、 醫 療 照 護 、 工 業 感 測 網 路 、 導 航 控 制 等 應 用 上 。<br />

Zigbee 可 以 利 用 電 池 供 電 設 備 的 低 載 、 低 頻 率 在 負 擔 得 起 的 成 本 下 建 構 網 路 骨 幹 。<br />

透 過 Zigbee 的 傳 輸 協 定 , 可 以 汲 取 出 所 接 收 到 信 號 的 強 度 ( RSSI ) , 藉 此 推 斷 訊 號<br />

源 ( reference tag ) 與 讀 取 器 ( reader tag ) 之 間 的 距 離 , 導 出 訊 號 源 所 在 的 座 標 位 置 ,<br />

這 種 定 位 的 方 式 相 對 於 GPS 能 夠 提 供 小 範 圍 的 準 確 定 位 。 那 麼 基 於 Zigbee 的 無 線 傳<br />

輸 與 定 位 , 是 否 可 以 提 供 小 範 圍 的 導 覽 服 務 , 以 幫 助 使 用 者 快 速 找 出 想 要 到 達 的 地<br />

點 與 方 式 呢 ?<br />

透 過 實 作 的 結 果 可 以 將 Zigbee 原 本 的 目 的 , 也 就 是 無 線 感 測 所 蒐 集 到 的 資 料 整<br />

合 成 資 訊 再 傳 輸 給 每 個 使 用 者 , 手 邊 具 有 結 合 Zigbee 行 動 裝 置 的 使 用 者 就 可 以 立 即<br />

了 解 身 邊 的 環 境 資 訊 , 以 達 到 方 便 的 目 的 。<br />

3


二 、 前 言 與 文 獻 回 顧<br />

此 份 計 劃 的 原 型 為 使 用 10~15 個 Zigbee 感 測 器 建 構 雛 形 無 線 定 位 骨 幹 網 絡 , 兩 個<br />

次 領 域 各 有 六 個 固 定 位 置 參 考 感 測 器 (Zigbee reference tag) 對 稱 地 布 置 其 中 , 有 一 固 定<br />

位 置 讀 取 器 (Reader tag) 佈 置 於 會 場 中 央 , 各 以 正 方 形 及 菱 型 代 表 之 。 固 定 讀 取 器 負 責 與<br />

所 有 參 考 感 測 器 及 一 閘 道 器 (gateway) 建 立 通 訊 。 中 央 與 一 筆 電 相 連 之 固 定 感 測 器 即 為<br />

閘 道 器 。 當 使 用 者 推 著 配 戴 Zigbee tag 之 購 物 車 在 工 作 空 間 中 漫 遊 時 , 系 統 即 開 始 經<br />

由 此 一 骨 幹 網 路 進 行 活 動 tag 位 置 之 計 算 , 隨 時 更 新 其 位 置 並 儲 存 於 筆 電 server 中 之<br />

資 料 庫 。<br />

當 智 慧 型 購 物 車 針 對 使 用 者 之 選 購 需 求 作 出 反 應 , 如 使 用 者 點 選 某 食 譜 , 即 會<br />

觸 發 request 指 令 向 database server 索 取 該 食 譜 所 屬 群 組 中 所 有 成 份 食 材 之 目 前 位 置 ,<br />

並 在 連 接 至 該 智 慧 型 購 物 車 之 嵌 入 式 LCD 顯 示 成 員 位 置 ( 在 各 次 領 域 之 相 對 位 置 ) 另<br />

一 圖 七 顯 示 該 智 慧 型 購 物 車 移 至 另 一 區 域 時 之 情 景 。User A,B 之 位 置 同 時 出 現 在 次<br />

領 域 2 之 購 物 車 LCD 螢 幕 內 。<br />

實 際 上 由 於 場 地 與 設 備 的 限 制 , 實 地 測 試 以 PC 機 房 為 測 試 環 境 , 並 將 蒐 集 感 測<br />

器 的 位 置 讀 取 器 縮 減 為 3 個 ,Database server 以 PC 機 房 中 的 一 台 主 機 代 替 , 以 開 發 板<br />

連 接 讀 取 器 代 替 可 以 四 處 移 動 的 智 慧 型 購 物 車 。 透 過 Database server 所 取 得 的 定 位 資<br />

訊 以 及 使 用 者 所 期 望 的 目 的 地 導 引 出 到 達 目 的 地 的 路 徑 , 並 且 隨 時 更 新 定 位 資 訊 以<br />

表 現 出 Zigbee 在 小 範 圍 定 位 以 及 Zigbee 傳 遞 資 訊 的 可 行 性 。<br />

4


三 、 設 計 原 理 分 析<br />

這 份 專 題 包 含 整 合 定 位 資 訊 的 伺 服 器 端 與 表 現 定 位 結 果 的 客 戶 端 。 其 中 伺 服 器 端<br />

必 須 處 理 各 個 位 置 接 受 器 所 讀 取 到 的 RSSI 轉 換 成 參 考 感 測 器 所 在 的 位 置 , 並 且 將 位<br />

置 資 訊 透 過 Zigbee 傳 遞 給 相 應 的 客 戶 端 。 而 客 戶 端 則 將 伺 服 器 端 所 傳 來 的 資 訊 顯 示 ,<br />

並 透 過 使 用 者 的 選 擇 表 示 出 相 應 的 路 徑 。<br />

3-1. 伺 服 器 接 收 RSSI 產 生 定 位 資 訊 的 方 式<br />

方 法 一 :<br />

透 過 讀 取 參 考 感 測 器 與 多 個 位 置 讀 取 器 的 RSSI , 直 接 將 RSSI 轉 換 成 距 離 關 係 ,<br />

藉 此 求 出 參 考 感 測 器 的 位 置 資 訊 。<br />

( 圖 片 : 三 點 定 位 )<br />

首 先 , 先 算 出 位 置 讀 取 器 之 間 的 距 離 , 再 利 用 位 置 讀 取 器 之 間 的 距 離 與 RSSI 的<br />

關 係 導 出 參 考 感 測 器 與 位 置 讀 取 器 的 距 離 , 以 及 必 須 的 參 數 。 分 別 是 R1, R2, R3, sin( a<br />

), sin( b ), sin( c ), cos( a ), cos( b ), cos( c )。<br />

利 用 公 式 :<br />

5


藉 由 旋 轉 矩 陣 , 將 向 量 旋 轉 再 以 此 為 單 位 長 度 向 量 計 算 : 。<br />

利 用 求 出 的 三 條 向 量 所 取 得 的 三 個 座 標 做 平 均 , 藉 此 推 算 出 參 考 感 測 器 的 位 置 。<br />

但 是 這 項 定 位 法 的 缺 點 在 於 ,RSSI 容 易 受 環 境 變 動 所 影 響 , 所 以 推 算 出 的 位 置 也 會<br />

有 所 誤 差 。<br />

方 法 二 :<br />

利 用 建 立 高 斯 模 組 的 方 式 推 算 參 考 感 測 器 的 位 置 。 高 斯 模 組 的 建 立 是 以 RSSI 蒐<br />

集 約 100 ~ 1000 筆 產 生 的 平 均 值 與 標 準 差 , 進 而 透 過 公 式 導 出 參 考 感 測 器 的 位 置 。<br />

6


利 用 公 式 :<br />

帶 入 先 前 蒐 集 所 推 算 的 平 均 值 μ 、 標 準 差 σ 以 及 每 個 位 置 讀 取 器 所 蒐 集 到 的 平<br />

均 RSSI 來 求 出 每 一 個 節 點 出 現 參 考 感 測 器 的 機 率 值 , 而 機 率 值 最 高 的 節 點 就 被 定 為<br />

參 考 感 測 器 所 在 的 位 置 。<br />

3-2. 伺 服 端 與 客 戶 端<br />

Zigbee 原 本 的 功 能 就 在 於 建 立 低 成 本 的 網 路 骨 幹 , 所 以 在 使 用 Zigbee 作 為 定 位<br />

用 途 時 也 同 時 可 以 利 用 Zigbee 作 為 訊 息 傳 遞 的 方 式 。 在 這 次 的 專 題 中 所 採 用 的 Zigbee<br />

網 路 設 備 為 Helicomm 的 EZ-Tracer, EZ-Tracer 包 含 負 責 接 收 定 位 資 訊 的 Master, 以<br />

及 建 構 網 路 骨 幹 並 作 為 位 置 接 收 器 的 Reader, 還 有 作 為 定 位 目 標 的 Tag。<br />

在 專 題 實 驗 的 環 境 中 , 以 伺 服 端 銜 接 Master 負 責 接 收 每 一 個 Reader 所 回 傳 的 定<br />

位 資 訊 演 算 後 由 改 寫 過 的 EZ-Tracer Demo Utility 進 行 演 算 再 將 演 算 的 結 果 回 傳 給<br />

Reader 。 而 銜 接 Reader 的 客 戶 端 收 到 Master 所 傳 送 來 的 演 算 結 果 , 透 過 自 行 撰 寫 的<br />

GTK+ 圖 形 介 面 顯 示 資 訊 。<br />

7


3-3. 裝 置 與 主 機 的 通 訊 方 式<br />

helicomm EZ-Tracer 所 提 供 的 Master 為 USB 介 面 , 而 Reader 則 是 RS232 介 面 。 雖<br />

然 在 介 面 上 有 所 差 異 , 但 在 使 用 上 都 能 以 Serial Programming 的 方 式 來 操 作 。 以 Linux<br />

的 devfs 為 例 , 當 Master 接 上 主 機 時 會 自 動 產 生 /dev/ttyUSB0 的 節 點 , 而 Reader 則 是<br />

使 用 /dev/ttyS0 來 存 取 。<br />

當 程 式 要 使 用 到 裝 置 時 需 要 透 過 Linux 的 System calls, 一 般 來 說 透 過 open( ) ,<br />

close( ),read( ),write( ) 就 可 以 對 裝 置 進 行 簡 單 的 控 制 , 但 實 際 上 在 使 用 前 必 須 透 過<br />

termios 針 對 設 定 相 應 的 baudrate 以 及 通 訊 屬 性 與 標 準 , 以 避 免 資 料 在 傳 輸 時 產 生 意<br />

外 的 錯 誤 。<br />

當 程 式 在 使 用 Zigbee 裝 置 做 資 料 傳 輸 是 透 過 open( ) 所 取 得 的 檔 案 描 述 子 以 write(<br />

) 將 Zigbee 的 Frame 寫 入 , 裝 置 接 收 到 來 自 主 機 的 Frame 再 將 Frame 送 出 。 而 裝 置 接<br />

收 到 Frame 時 透 過 read( ) 取 得 接 收 到 的 Frame。<br />

Control Header<br />

Link Quality<br />

Destination<br />

Payload Length<br />

Payload<br />

XOR Checksum<br />

(1)<br />

Indicator<br />

Address<br />

(1)<br />

(0 ~ 97)<br />

(1)<br />

(1)<br />

(2)<br />

根 據 Zigbee 的 標 準 Zigbee Frame 的 型 態 分 為 兩 類 四 種 , 以 Control Header 的 前 4<br />

個 bits 所 決 定 , 而 Frame 的 參 數 有 上 述 六 種 。 如 果 直 接 在 程 式 中 直 接 以 陣 列 表 示 出<br />

Frame 不 免 喪 失 一 些 程 式 的 可 讀 性 以 及 維 護 性 。 是 故 , 當 程 式 在 存 取 裝 置 時 不 是 直 接<br />

產 生 Frame 而 是 透 過 以 下 的 型 態 與 函 式 存 取 Frame。<br />

typedef enum {<br />

CMD_REQUEST,<br />

CMD_RESPONSE,<br />

DATA_REQUEST,<br />

DATA_ACK<br />

}FrameType;<br />

typedef struct {<br />

unsigned short smac;<br />

8


int deviceFd;<br />

}zb_Reader;<br />

typedef struct {<br />

unsigned char data[ZIGBEE_FRAME_SIZE];<br />

}zb_Frame;<br />

int zb_initReader( );<br />

int zb_releaseReader( );<br />

int zb_send( );<br />

int zb_recv( );<br />

int zb_setFrameType( );<br />

int zb_setFrameDestSmac( );<br />

int zb_setFrameData( );<br />

FrameType zb_getFrameType( );<br />

unsigned short zb_getFrameSrcSmac( );<br />

int zb_getFrameData( );<br />

3-4. 伺 服 端 與 客 戶 端 的 通 訊 方 式<br />

透 過 上 述 所 定 義 的 函 式 , 伺 服 端 可 以 不 斷 接 收 各 個 Reader 所 接 收 到 的 RSSI 以 及<br />

送 出 新 的 定 位 資 訊 , 而 客 戶 端 在 接 收 到 則 更 新 目 前 所 顯 示 的 資 訊 , 之 間 的 通 訊 是 以<br />

類 似 UDP 的 方 式 傳 遞 。 以 客 戶 端 的 使 用 為 例 :<br />

if(!reader_connected) {<br />

reader_connected = zb_initReader(&reader, ZB_TTY);<br />

}<br />

while(reader_connected) {<br />

if(zb_recv(&reader, &frame)) {<br />

zb_getFrameData(&frame, data);<br />

infoAnalysis(data);<br />

}<br />

}<br />

透 過 這 樣 的 流 程 使 客 戶 端 接 收 來 自 伺 服 端 的 定 位 資 訊 。<br />

9


3-5. 客 戶 端 顯 示 的 相 關 資 訊<br />

在 這 個 專 題 中 以 PXA255 開 發 版 作 為 客 戶 端 , 來 貼 近 一 個 合 併 購 物 車 的 行 動 裝 置 。<br />

透 過 PXA255 的 螢 幕 可 以 顯 示 出 環 境 的 地 圖 以 及 目 前 所 在 的 位 置 , 為 了 要 讓 PXA255<br />

可 以 顯 示 出 這 些 資 訊 或 是 接 收 使 用 者 的 輸 入 , 必 須 使 用 一 些 圖 形 函 式 庫 來 達 成 。<br />

華 亨 科 技 的 PXA255 開 發 版 所 使 用 的 圖 形 介 面 函 式 庫 為 GTK+ 1.2 , 而 GTK+ 有<br />

一 項 關 聯 的 產 物 Glade ,Glade 是 一 項 透 過 圖 形 介 面 來 產 生 圖 形 介 面 的 程 式 。 透 過<br />

Glade 可 以 快 速 的 產 生 程 式 介 面 的 雛 型 以 及 自 動 引 用 GTK+ 圖 形 介 面 函 式 庫 , 使 得 在<br />

編 寫 圖 形 程 式 只 要 專 注 於 程 式 的 邏 輯 , 以 及 回 應 圖 形 介 面 的 事 件 。<br />

以 客 戶 端 的 程 式 來 說 ; 程 式 的 邏 輯 就 是 接 收 來 自 伺 服 端 的 定 位 資 訊 , 顯 示 出 目<br />

前 所 在 的 位 置 , 以 及 更 新 最 短 路 徑 的 狀 態 ; 而 來 自 使 用 者 的 請 求 則 是 透 過 圖 形 介 面<br />

的 按 鈕 觸 發 事 件 , 更 改 程 式 的 狀 態 。 程 式 的 邏 輯 以 一 個 refresh( ) 的 函 式 完 成 , 經 由<br />

GTK+ 的 gtk_idle_add( ) 由 gtk_main( ) 在 圖 形 介 面 閒 置 時 不 斷 呼 叫 , 使 程 式 具 有 類 似<br />

多 工 的 功 能 來 更 新 資 訊 。<br />

當 以 Glade 完 成 介 面 的 設 計 時 會 產 生 幾 份 C 程 式 碼 檔 案 , 分 別 是 callbacks.c/.h 、<br />

interface.c/.h、support.c/.h、main.c , 以 及 autogen.sh 。 透 過 修 改 這 些 文 件 就 可 以 回 應 事 件<br />

觸 發 的 行 為 , 以 及 指 定 makefile 所 產 出 的 執 行 檔 平 台 。<br />

3-6. 確 認 圖 形 介 面 的 運 作 正 常<br />

當 程 式 完 成 時 必 須 透 過 開 發 板 的 bootloader 以 及 開 發 環 境 的 tftp server 進 行 燒 錄 的<br />

動 作 , 如 果 圖 形 介 面 不 如 預 期 所 運 作 就 必 須 修 改 並 重 新 燒 錄 , 這 樣 的 動 作 十 分 瑣 碎<br />

而 且 一 燒 就 是 二 十 分 鐘 。 事 實 上 透 過 Linux 搭 配 GTK+ 套 件 就 可 以 在 開 發 環 境 中 呈 獻<br />

出 圖 形 介 面 運 作 的 樣 子 , 在 開 發 環 境 中 測 試 完 成 才 透 過 cross-compiler 產 生 開 發 板 所<br />

使 用 的 程 式 。<br />

以 目 前 的 Linux 發 行 板 來 說 , 幾 乎 沒 有 提 供 GTK+ 1.2 以 及 Glade 0.6 的 套 件 讓 使<br />

10


用 者 下 載 安 裝 , 所 以 必 須 自 行 到 GTK+ & Glade 的 官 方 網 站 下 載 。 經 過 編 譯 三 部 曲<br />

(./configure && make && make install) 就 可 以 在 開 發 環 境 使 用 。<br />

3-7. 最 短 路 徑 的 表 示<br />

程 式 在 接 收 到 目 前 的 所 在 位 置 以 及 使 用 者 所 選 擇 的 目 的 地 時 , 必 須 表 示 出 一 條<br />

到 達 目 的 地 的 最 短 路 徑 。 在 此 專 題 中 是 以 Dijkstra 的 演 算 法 來 求 出 最 短 路 徑 ,Dijkstra<br />

演 算 法 的 時 間 複 雜 度 為 O(|E| + |V|log|V| ) , 所 以 在 表 示 路 徑 時 只 會 以 少 量 的 頂 點 連 線<br />

顯 示 出 空 間 中 主 要 的 幹 道 , 當 目 的 地 或 是 所 在 位 置 更 新 時 會 選 取 附 近 的 最 近 頂 點 作<br />

為 終 點 或 是 起 點 。<br />

11


四 、 軟 硬 體 系 統 說 明<br />

上 圖 是 硬 體 配 置 的 大 概 架 構 , 透 過 Server 連 接 Master 裝 置 可 以 向 週 遭 的 Reader<br />

索 取 RSSI 並 且 傳 輸 定 位 結 果 給 裝 有 Reader 的 Client, 而 中 間 的 協 定 是 Zigbee。<br />

上 圖 是 實 際 運 作 的 硬 體 配 置 , 前 端 的 主 機 為 收 集 RSSI 運 算 定 位 資 訊 的 Server,<br />

而 擺 在 後 方 椅 子 上 的 為 接 收 位 置 資 訊 的 開 發 板 以 及 裝 置 。<br />

12


上 圖 表 示 Server 與 Client 之 間 的 通 訊 架 構 。<br />

上 圖 表 示 Server 透 過 Master 向 Reader 汲 取 RSSI。<br />

上 圖 表 示 Server 傳 遞 位 置 給 Client 的 流 程 。<br />

13


上 圖 為 程 式 在 開 發 平 台 測 試 , 左 上 角 的 紅 點 為 起 始 位 置 , 右 下 角 的 綠 點 為 目 的<br />

位 置 , 兩 者 皆 是 透 過 選 取 產 生 , 而 程 式 自 動 根 據 起 始 點 與 目 的 地 附 近 的 節 點 求 出 最<br />

短 的 路 徑 。<br />

五 、 團 隊 分 工 合 作 方 式<br />

由 於 這 份 專 題 只 有 一 人 處 理 , 所 以 大 部 分 的 協 助 都 是 來 自 石 志 雄 教 授 以 及 梁 博<br />

丞 學 長 。 架 構 上 的 問 題 與 學 長 討 論 過 後 再 向 教 授 詢 問 可 行 性 , 然 後 才 由 我 修 改 程 式 。<br />

下 文 的 結 果 也 是 由 於 學 長 的 幫 助 完 成 場 地 高 斯 模 組 的 建 置 , 才 得 以 取 得 定 位 的 結 果 。<br />

14


六 、 成 果 與 討 論<br />

上 圖 是 整 體 裝 置 的 照 片 , 左 方 的 開 發 板 透 過 RS232 跳 線 連 接 至 右 上 方 的 Reader<br />

以 接 收 來 自 Server 的 位 置 資 訊 , 而 Reader 下 方 則 是 散 布 定 位 資 訊 的 Tag。<br />

在 開 發 版 上 可 以 接 收 來 自 Server 的 位 置 資 訊 並 顯 示 , 以 及 根 據 目 的 地 產 生 一 條<br />

最 短 路 徑 , 除 了 用 來 廣 播 RSSI 的 Tag 外 還 放 置 了 Reader 供 開 發 版 使 用 。<br />

上 圖 為 當 時 所 在 的 位 置 。<br />

15


從 相 對 的 一 角 觀 看 。<br />

16


經 過 移 動 之 後 , 新 的 位 置 資 訊 傳 入 並 更 新 最 短 路 徑 。<br />

而 該 時 的 位 置 於 該 處 。<br />

17


透 過 視 窗 下 方 的 按 鈕 可 以 由 使 用 者 決 定 目 的 地 , 以 幫 助 使 用 者 了 解 最 短 路 徑 。<br />

上 圖 為 使 用 者 點 擊 Worst seat 的 按 鈕 所 指 出 的 路 徑 。<br />

上 圖 為 使 用 者 點 擊 Best seat 的 按 鈕 所 指 出 的 路 徑 。<br />

18


即 使 位 置 改 到 別 處 也 可 以 更 新 從 該 位 置 到 達 目 的 地 的 最 短 路 徑 。<br />

上 圖 是 Worst seat 更 新 過 的 路 徑 。<br />

上 圖 是 Best seat 更 新 過 的 路 徑 。<br />

19


七 、 結 論<br />

雖 然 在 定 位 上 仍 然 有 所 差 異 但 是 透 過 一 種 無 線 協 定 就 可 以 擁 有 網 路 通 訊 以 及 定<br />

位 的 功 能 , 加 上 Zigbee 具 有 低 成 本 的 優 勢 , 雖 然 wifi 也 可 以 透 過 訊 號 衰 減 來 達 成 定<br />

位 效 果 , 但 是 wifi 在 環 境 監 控 的 部 份 就 比 不 上 Zigbee。 專 題 的 結 果 印 證 了 Zigbee 與<br />

購 物 車 結 合 的 可 行 性 , 從 而 達 到 購 物 車 的 定 位 效 果 以 提 供 簡 易 導 覽 。<br />

八 、 參 考 文 獻<br />

GTK+ Reference Manual<br />

Linux 程 式 設 計 教 學 手 冊 第 四 版 ,ISBN :978-986-181-549-7<br />

Serial Programming HOWTO<br />

ZigBee 開 發 手 冊 ,ISBN:978-957-216-924-7<br />

戴 弘 棋 , 基 於 高 斯 混 合 模 型 系 統 之 室 內 定 位 系 統 設 計 與 實 作 。<br />

20


九 、 附 錄<br />

Zigbee 通 訊 實 作 zigbee.c:<br />

#include "zigbee.h"<br />

#include <br />

#include <br />

#include <br />

#include <br />

#include <br />

#include <br />

#include <br />

#include <br />

#include <br />

#include <br />

#include <br />

static void dumpMem(unsigned char * ptr, int lineLen, int<br />

dumpLen)<br />

{<br />

int i;<br />

for(i = 0; i < dumpLen; i++) {<br />

printf("%2X ", ptr[i]);<br />

if((i%lineLen == lineLen-1)||(i == dumpLen-1)) puts("");<br />

}<br />

}<br />

static int zb_setChecksum(zb_Frame * frame)<br />

{<br />

/* dataLength + (ctrlHeader(1) + LQI(1) + destSmac(2) +<br />

dataLengthLength(1)) */<br />

int frameLength = frame->data[4] + 5;<br />

unsigned char xorChecksum = 0;<br />

for(int i = 0; i < frameLength; i++) {<br />

xorChecksum ^= frame->data[i];<br />

}<br />

frame->data[frameLength] = xorChecksum;<br />

return true;<br />

}<br />

static int zb_frameCheck(zb_Frame * frame)<br />

{<br />

int frameLength = frame->data[4] + 5;<br />

21


unsigned char xorChecksum = 0;<br />

for(int i = 0; i data[i];<br />

}<br />

return 0 == xorChecksum;<br />

}<br />

static int nonBlockingRead(int fd, void * buf, size_t size<br />

) /* ioctl implementation */<br />

{<br />

int nread;<br />

ioctl(fd, FIONREAD, &nread);<br />

if((nread


puts("open failed.");<br />

success = false;<br />

}<br />

if(success) puts("open finish.");<br />

if(success) {<br />

struct termios fd_opt;<br />

tcgetattr(fd, &fd_opt);<br />

cfsetospeed(&fd_opt, B38400);<br />

cfsetispeed(&fd_opt, B38400);<br />

fd_opt.c_iflag &= ~(INPCK | PARMRK | IXON | IXOFF);<br />

fd_opt.c_iflag |= (IGNPAR);<br />

fd_opt.c_cflag &= ~(CSIZE | CSTOPB | PARENB);<br />

fd_opt.c_cflag |= (CS8 | CREAD);<br />

fd_opt.c_lflag &= ~(ICANON | ECHO | ECHOE | ISIG);<br />

fd_opt.c_cc[VTIME] = 1;<br />

fd_opt.c_cc[VMIN] = 0;<br />

tcflush(fd, TCIFLUSH);<br />

int result;<br />

result = tcsetattr(fd, TCSANOW, &fd_opt);<br />

if(-1 == result) {<br />

while(-1 != close(fd));<br />

puts("set_attr failed.");<br />

success = false;<br />

}<br />

}<br />

if(success) puts("set_attr finish.");<br />

if(success) {<br />

zb_Frame loFrame;<br />

zb_Frame readFrame;<br />

unsigned char frameData[] = {0x8B};<br />

zb_setFrameType(&loFrame, CMD_REQUEST);<br />

zb_setFrameDestSmac(&loFrame, 0xFFFE);<br />

zb_setFrameData(&loFrame, frameData, 1);<br />

zb_setChecksum(&loFrame);<br />

completelyWrite(fd, loFrame.data, 7);<br />

success = false;<br />

for(int i = 0; i < 100; i++) {<br />

23


if(read(fd, readFrame.data, ZIGBEE_FRAME_SIZE)) {<br />

puts("recv data");<br />

dumpMem(readFrame.data, 8, 16);<br />

if(zb_frameCheck(&readFrame)) {<br />

reader->smac = ((unsigned short)readFrame.data[2]<br />

deviceFd = fd;<br />

success = true;<br />

}<br />

break;<br />

}<br />

}<br />

}<br />

if(!success) {<br />

close(fd);<br />

}<br />

return success;<br />

}<br />

int zb_releaseReader(zb_Reader * reader)<br />

{<br />

close(reader->deviceFd);<br />

}<br />

int zb_send(zb_Reader * reader, zb_Frame * frame)<br />

{<br />

return completelyWrite(reader->deviceFd, frame->data,<br />

ZIGBEE_FRAME_SIZE);<br />

}<br />

int zb_recv(zb_Reader * reader, zb_Frame * frame)<br />

{<br />

nonBlockingRead(reader->deviceFd, frame->data,<br />

ZIGBEE_FRAME_SIZE);<br />

return zb_frameCheck(frame);<br />

}<br />

int zb_setFrameType(zb_Frame * frame, FrameType type)<br />

{<br />

switch(type) {<br />

case CMD_REQUEST :<br />

frame->data[0] &= 0x0F;<br />

24


frame->data[0] |= 0x80;<br />

break;<br />

case CMD_RESPONSE :<br />

frame->data[0] &= 0x0F;<br />

frame->data[0] |= 0xC0;<br />

break;<br />

case DATA_REQUEST :<br />

frame->data[0] &= 0x0F;<br />

frame->data[0] |= 0xA0;<br />

break;<br />

case DATA_ACK :<br />

frame->data[0] &= 0x0F;<br />

frame->data[0] |= 0xE0;<br />

break;<br />

default :<br />

return false;<br />

}<br />

return true;<br />

}<br />

int zb_setFrameDestSmac(zb_Frame * frame, unsigned short smac<br />

)<br />

{<br />

frame->data[2] = (unsigned char)(smac >> 8);<br />

frame->data[3] = (unsigned char)(smac % 0x00FF);<br />

return true;<br />

}<br />

int zb_setFrameData(zb_Frame * frame, const void * data,<br />

size_t dataLength)<br />

{<br />

if(dataLength > 96) {<br />

return false;<br />

} else {<br />

frame->data[4] = dataLength;<br />

memcpy(&frame->data[5], data, dataLength);<br />

}<br />

return true;<br />

}<br />

FrameType zb_getFrameType(zb_Frame * frame)<br />

25


{<br />

switch (frame->data[0] & 0xF0) {<br />

case 0x80 :<br />

return CMD_REQUEST;<br />

case 0xC0 :<br />

return CMD_RESPONSE;<br />

case 0xA0 :<br />

return DATA_REQUEST;<br />

case 0xE0 :<br />

return DATA_ACK;<br />

default :<br />

return -1;<br />

}<br />

}<br />

unsigned short zb_getFrameSrcSmac(zb_Frame * frame)<br />

{<br />

unsigned short smac;<br />

smac = ((unsigned short)frame->data[2] data[3];<br />

return smac;<br />

}<br />

int zb_getFrameData(zb_Frame * frame, void * dest, size_t *<br />

dataLength)<br />

{<br />

size_t srcLength = frame->data[4];<br />

*dataLength = srcLength;<br />

memcpy(dest, &frame->data[5], srcLength);<br />

return true;<br />

}<br />

26

Hooray! Your file is uploaded and ready to be published.

Saved successfully!

Ooh no, something went wrong!