2011-01-20 12 views
0

はシリアルポートにアクセスするために書いた粗コードです。私のデータを送信し、57600のボーレートを持つマイクロコントローラです。コードを一度実行して結果を得ましたが、ウィンドウを閉じた後、コンピュータがハングアップしました。私はCtrl + Alt + Delキーを押して、プロセスの下で私のプログラムがまだ実行されているのを見た。私もそれを閉じることができません。Windowsを使用しているときにプログラムがハングアップする

int n = 20; 
char szBuff[20 + 1] = {0}; 

HANDLE hSerial; 
DCB dcbSerialParams = {0}; 
COMMTIMEOUTS timeouts={0}; 
DWORD dwBytesRead = 20; 

dcbSerialParams.DCBlength=sizeof(DCB); 

hSerial = CreateFile("COM5", 
       GENERIC_READ | GENERIC_WRITE, 
       0, 
       0, 
       OPEN_EXISTING, 
       FILE_ATTRIBUTE_NORMAL, 
       0); 


if(hSerial==INVALID_HANDLE_VALUE) 
{ 
    if(GetLastError()==ERROR_FILE_NOT_FOUND) 
    { 
    puts ("cannot open port!"); 
    } 

    puts ("invalid handle value!");         
} 

if (!GetCommState(hSerial, &dcbSerialParams)) 
{ 
    puts ("error getting state"); 
} 

dcbSerialParams.BaudRate=CBR_57600; 
dcbSerialParams.ByteSize=8; 
dcbSerialParams.StopBits=ONESTOPBIT; 
dcbSerialParams.Parity=NOPARITY; 

if(!SetCommState(hSerial, &dcbSerialParams)) 
{ 
    puts ("error setting port state"); 
} 


while (1) 
{ 

    if(!ReadFile(hSerial, szBuff, n, &dwBytesRead, NULL)){ 
    puts ("serial read error fail!"); 
    } 

    else 
    { 
    printf ("%s\n" , szBuff); 
    } 

} 
+1

あなたは 'while 1'を使用していますが、どのようにプログラムが終了すると思いますか? – stijn

+0

私はポートから連続してデータを読みたいと思っています。間違っていると思います。私はこれをより効率的にやり遂げる方法を教えていただけますか? – user582485

+0

それはそれほど間違っているわけではありませんが、プログラムを終了するときに何か言いたいことがあります。例えば 'puts(" serial read error fail! ")の代わりに' 'puts(" serial read error fail!これは既に(私が正しいとすれば)シリアルデバイスが故障したり切断されたときにループを終了するはずです。 – stijn

答えて

1

これはバグの多いシリアルポートドライバのようです。 Why do some process stay in Task Manager after they've been killed?を参照してください。プログラムを強制終了すると、保留中のすべてのI/O操作がキャンセルされるまで、プログラムは終了しません。

+0

おそらく、彼はまだポートが不自由な時にもそれから読むことを試みています(エラーでwhileループから何も外れません)。 –

+0

@Tim:永遠にループするプログラムは本質的にバグではなく、 'tail -f'のように強制終了したときに終了するように設計することもできます。このプログラムはI/Oをブロックしているので、100%CPUを使い果たすことはありません。 –

+0

私は同意する、おそらくバギードライバーだ。私は最終的に+1を追加して、私のコメントと一緒に行くようになりました。今度はもう一度投票します。 –

0

while(1)でループする場合は、アプリに何らかのタイプの停止を定義する必要があります。

オプション1:マイクロコントローラは、中断するために使用する終了コマンドまたは文字を送信する必要があります。

オプション2:(1)の代わりにいくつかのタイプのタイムアウト。

オプション3:信号を捕まえてからwhile()を中断してください。

他にもたくさんのオプションがあります。

関連する問題