NI產品與技術 討論區

取消
顯示結果 
搜尋替代 
您的意思是: 

ibwat 與 ibrda

已解決!
前往解決方案

您好,我想請問api使用問題,我是使用usb的GPIB與HP34401儀器。

我目前要測量電阻的阻值用以下的api順序去取值。

 

ibclr(devID1);  //清理裝置

 

ibwrta(devID1, _cmd_READ, _cmd_READ.Length); // _cmd_READ 為 "READ?"

ibwait(devID1, CMPL); // GPIB.CMPL 為 (1<<8) 使用ni488.h設定的

 

if( (ThreadIbsta() & ERR ) != 0 ) return ; //有錯就離開

 

ibrda(devID1, _ReadBuf, _ReadBuf.Length);  /ReadBuf 為 256 個byte
ibwait(devID1, CMPL);  // GPIB.CMPL 為 (1<<8) 使用ni488.h設定的

 

if( (ThreadIbsta() & ERR ) != 0 ) return ; //有錯就離開

 

int tReadSize = ThreadIbcntl();

//..以下流程為 當tReadSize 不為 0 ,也就是 ThreadIbcntl() 傳回buffer的資料大小,如此我再去抓資料回來

 

經過以上的流程跑,剛開始可能會_ReadBuf會正常有資料進來,但是可能跑了幾秒鐘(約10秒不一定)之後,

就會出現錯誤,錯誤的原因是 tReadSize 有大小 (例如傳回的資料是16個byte),

但是在_ReadBuf卻是沒有資料的,所以我在做parse的時候會出問題(parse _ReadBuf)

因為_ReadBuf是空的,我是在保證資料會傳來的狀態下(也就是tReadSize不為0)做parse的。

 

請問~既然我用了非同步I/O且用ibwait去等待I/O完成,那為什麼我再I/O完成後_ReadBuf裡面可能會抓不到資料?

還是我的程式流程有問題~謝謝指教。

 

 


              

0 積分
1 條訊息(共 4 條)
7,519 檢視

請問您是否參考範例?

 

http://digital.ni.com/public.nsf/allkb/E0D14AB889CBF8E5862572B8006B22D3?OpenDocument

 

建議先從最簡單範例著手。

 

如果有解決到您的問題麻煩您勾選已接受解答,並且給我一個獎勵!謝謝~~~

2 條訊息(共 4 條)
7,506 檢視

首先謝謝您的回應,根據您的指示我參考了範例,不過這些範例我之前有看過了。

只是在wait部分沒有改成向範例一樣的流程,後來我依據下面的位址的範例,改寫了流程但是仍然會出現讀取不到的問題。

C:\Documents and Settings\All Users\Documents\National Instruments\NI-488.2\Examples\Standard C\Asyncquery

我在想是否是因為我使用usb?而我電腦是單核心,有可能前一個api說有資料但是可能資料還沒上送buffer就被我抓到了嗎?

以下是我改寫後的程式碼。如有錯誤請指正我謝謝。

 

                ibwrta(devID1, _cmd_READ, _cmd_READ.Length);

                while ((ThreadIbsta() & CMPL) == 0)
                {
                    ibwait(devID1, 0);
                    if ( (ThreadIbsta() & ERR) != 0)
                    {                        
                        ibonl(devID1, 0);
                        return ;
                    }

                }

                byte[] _ReadBuf = new byte[20];

                ibrda(devID1, _ReadBuf, _ReadBuf.Length);

 

                while ((ThreadIbsta() & CMPL) == 0)
                {
                   

                    ibwait(devID1, 0);
                    if ( (ThreadIbsta() & ERR) != 0)
                    {
                        ibonl(devID1, 0);
                        return ;
                    }

                    

                   }

 

                    int _tReadSize = ThreadIbcntl();
                    if (_tReadSize != 0)
                    {

                         //這裡我將_tReadSize讀取到的大小,將_ReadBuf 寫入檔案,這裡保證不會錯,而且我用debug模式,會先將

                         //char[] 轉換成 double在寫入檔案

                        //而我現在不定時的會收到_tReadSize = 16但是_ReadBuf卻是以'\0'填滿的東西。所以導致轉換出來是有問題的

                    }

 

以上的程式碼是跑在一個Thread裡面的,有另一個Thread會在去把結果值顯示在畫面上面(保證是執行緒安全的)

所以我不知道是因為什麼原因,導致ThreadIbcntl()傳回16而我去抓buffer卻是'\0'填滿的,謝謝。

(基本上其他command透過ibwra送給儀器,事都可以運作的,只有在這邊會有奇怪的問題@@所以我在想是否流程少了什麼,謝謝指教)

0 積分
3 條訊息(共 4 條)
7,501 檢視
解決方案
由主題作者所接受 colinCk
你的程式有考慮 wait 的部分嗎?因為當你下指令 write,然後要讀回傳的資料 read 的中間,會視情況需要加上等待的時間,不然程式碼執行得很快,可是你的儀器還沒有這麼快反應把資料送進來,那讀到的就會都不正確或是是空的囉。例如若你的資料一定會在 5秒內回傳,那麼在 write 之後,等待 5 秒的,再去做 read 的動作,才會讀得到喔。
4 條訊息(共 4 條)
7,494 檢視