serielle Kommunikation streikt ab 50 byte/s



  • Hallo

    Ich hab es jetzt endlich geschafft eine serielle Kommunikation zwischen PC und Microcontroller auf zu bauen, was im Allgemeinen auch ganz gut funktioniert. Ich hab den Microcontroller so programmiert, dass es alle 20ms ein Byte schickt dass dem Inkrement des vorherigen entspricht. (Also ein Sägezahn)

    Diesen Datenstrom soll das Programm nun empfangen und grahisch darstellen, normalerweise sollte das so aussehen:

    http://www.directupload.net/file/d/963/ZD9Rbrj6_jpg.htm

    doch wenn ich zb alle 10ms ein byte schicke, dann funktioniert am Anfang alles ganz normal, aber nach ca 20s sieht es dann so aus:

    http://www.directupload.net/file/d/963/64IxAAQM_jpg.htm

    das sieht aus als ob da Bytes ausgelassen würden, und nur jedes 4. ankommen würde. Das ändert sich auch nicht wenn ich ganze Frames (zb 64bytes) einlese, 1 Frame wird dann zwar zur Gänze gelesen, aber die folgenden 3 nicht mehr.

    Hat jemand eine Ahnung woran das liegen könnte? Danke.

    Hier mein Code:

    #include <windows.h>
    #include <stdio.h>
    
    #define		WM_COMMEVENT	(WM_USER+1)
    
    #define		POINTS			1024
    #define		FRAME			64
    
    LRESULT CALLBACK WndProc (HWND, UINT, WPARAM, LPARAM);
    
    int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR szCmdLine, int iCmdShow)
    {
    	static TCHAR szAppName[] = TEXT ("COMM");
    	HWND		hwnd;
    	MSG			msg;
    	WNDCLASS	wndclass;
    
    	wndclass.style			= CS_HREDRAW | CS_VREDRAW;
    	wndclass.lpfnWndProc	= WndProc;
    	wndclass.cbClsExtra		= 0;
    	wndclass.cbWndExtra		= 0;
    	wndclass.hInstance		= hInstance;
    	wndclass.hIcon			= LoadIcon (NULL, IDI_APPLICATION);
    	wndclass.hCursor		= LoadCursor (NULL, IDC_ARROW);
    	wndclass.hbrBackground	= (HBRUSH) GetStockObject (WHITE_BRUSH);
    	wndclass.lpszMenuName	= NULL;
    	wndclass.lpszClassName	= szAppName;
    
    	if (!RegisterClass (&wndclass))
    	{
    		MessageBox (NULL, TEXT (" Dieses Programm setzt Windows NT voraus!"), TEXT ("Warnung:"), MB_ICONERROR);
    		return (0);
    	}
    
    	hwnd = CreateWindow (szAppName, TEXT ("COMM"), WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, NULL, NULL, hInstance, NULL);
    
    	ShowWindow (hwnd, iCmdShow);
    	UpdateWindow (hwnd);
    
    	while (GetMessage (&msg, NULL, 0, 0))
    	{
    		TranslateMessage (&msg);
    		DispatchMessage (&msg);
    	}
    	return msg.wParam;
    }
    
    HANDLE			RS232;
    HANDLE			Thread;
    DWORD			events;
    UINT			UM_RECEIVE;
    HWND			_hwnd;
    bool			run;
    
    DWORD WINAPI WaitComm(PVOID pParam)
    {
    	int frame_count=0;
    
    	while(run)
    	{
    		if(WaitCommEvent(RS232,&events,NULL))
    		{
    							//MessageBeep(-1);
    			frame_count++;
    			if(frame_count>=FRAME)
    			{
    				frame_count=0;
    				SendMessage(_hwnd,WM_COMMEVENT,NULL,NULL);
    				//MessageBeep(-1);
    			}
    		}else{
    			TCHAR			szbuffer[50];
    			sprintf(szbuffer,TEXT("error: %d"),GetLastError());
    			MessageBox(NULL,szbuffer,TEXT("Warnung"),MB_ICONERROR);
    		}
    	}
    	return 0;
    
    }
    
    LRESULT CALLBACK WndProc (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
    {
    
    	// don't forget 'static' in WndProc variables!
    
    	static unsigned char	data[FRAME];
    	static int				count;
    	static POINT			line[POINTS];
    	static POINT			size;
    
    	switch(message)
    	{
    	case WM_CREATE:
    
    		DCB			settings;
    
    		RS232=CreateFile(TEXT("COM1"),GENERIC_READ | GENERIC_WRITE,0,NULL,OPEN_EXISTING,NULL,NULL);
    		if (RS232 == INVALID_HANDLE_VALUE) 
    		{
    			MessageBox(NULL,TEXT("CreateFile failed"),TEXT ("Warning:"),MB_ICONERROR);
    			return 0;
    		}
    
    		if(!GetCommState(RS232,&settings))
    		{
    			MessageBox(NULL,TEXT("GetCommState failed"),TEXT ("Warning:"),MB_ICONERROR);
    			return 0;
    		}
    		settings.BaudRate=CBR_19200;
    		settings.ByteSize=8;
    		settings.Parity=NOPARITY;
    		settings.StopBits=ONESTOPBIT;
    
    		if(!SetCommState(RS232,&settings))
    		{
    			MessageBox(NULL,TEXT("CreateThread failed"),TEXT ("Warning:"),MB_ICONERROR);
    			return 0;
    		}
    		SetCommMask(RS232,EV_RXCHAR);
    
    		_hwnd=hwnd;
    		run=true;
    		Thread=CreateThread(NULL,NULL,WaitComm,NULL,NULL,NULL);
    		if(!Thread)
    		{
    			MessageBox(NULL,TEXT("CreateThread failed"),TEXT ("Warning:"),MB_ICONERROR);
    			return 0;
    		}
    
    		count=0;
    		SetTimer(hwnd,1,100,NULL);
    
    		return 0;
    
    	case WM_SIZE:
    
    		size.x=LOWORD(lParam);
    		size.y=HIWORD(lParam);
    		return 0;
    
    	case WM_TIMER:
    
    		InvalidateRect(hwnd,NULL,true);
    		return 0;
    
    	case WM_COMMEVENT:
    
    		DWORD		received_bytes;
    		int			i;
    
    		if(!ReadFile(RS232,data,FRAME,&received_bytes,NULL))
    		{
    			MessageBox(NULL,TEXT("ReadFile failed"),TEXT ("Warning:"),MB_ICONERROR);
    			return 0;
    		}
    		if(received_bytes!=FRAME)
    		{
    			MessageBox(NULL,TEXT("not all bytes received"),TEXT ("Warning:"),MB_ICONERROR);
    			return 0;
    		}
    
    		for(i=0;i<FRAME;i++)
    		{
    			count++;
    			if(count>=POINTS)
    			{
    				count=0;
    			}
    			line[count].x=size.x*count/POINTS;
    			line[count].y=size.y*data[i]/256;
    		}
    		//InvalidateRect(hwnd,NULL,true);
    		return 0;
    
    	case WM_PAINT:
    
    		HDC				hdc;
    		PAINTSTRUCT		ps;
    		TCHAR			szbuffer[50];
    
    		hdc = BeginPaint(hwnd,&ps);
    		//TextOut(hdc,0,0,szbuffer,sprintf(szbuffer,TEXT("data: %d"),count));
    		Polyline(hdc,line,POINTS);
    
    		EndPaint(hwnd,&ps);
    		return 0;
    
    	case WM_DESTROY:
    
    		KillTimer(hwnd,1);
    		run=false;
    		ExitProcess(0);
    		//PostQuitMessage(0);
    		return 0;
    
         }
    
         return DefWindowProc (hwnd, message, wParam, lParam) ;
    }
    

Anmelden zum Antworten