PIC Vietnam

PIC Vietnam (http://www.picvietnam.com/forum/index.php)
-   Giao tiếp cổng COM và LPT (http://www.picvietnam.com/forum/forumdisplay.php?f=44)
-   -   Cho hỏi về giao tiếp RS232 của PIC16F877A (http://www.picvietnam.com/forum/showthread.php?t=796)

enti 15-12-2006 09:43 AM

Cho hỏi về giao tiếp RS232 của PIC16F877A
 
Hiện tôi dùng PIC16F877A để giao tiếp với máy tình qua cổng COM, chương trình trên PC viết bằng VB có chức năng lấy giờ từ internet và truyền cho PIC. Hiện tôi đang thắc mắc vấn đề này. PIC có một ngắt nhận RS232, #INT_RDA, nhưng tôi không biết khi nào thì ngắt này xảy ra, mỗi lần xảy ra nó nhận dữ liệu như thế nào, vì nếu PC truyền 6 số kiểu integer thì PIC nhận như thế nào, còn nếu PC truyền 1 biến chuỗi (ghép tất cả 6 biến kia lại ) thì PIC nhận như thế nào. và khi truyền thì nó truyền dữ liệu theo dạng nào. Nếu tôi truyền ngay số nguyên 14 thì PIC nhận là 0E? Ai biết về ngắt này thì giúp tôi 1 chút

namqn 15-12-2006 06:49 PM

Trích:

Nguyên văn bởi enti (Post 6362)
Hiện tôi dùng PIC16F877A để giao tiếp với máy tình qua cổng COM, chương trình trên PC viết bằng VB có chức năng lấy giờ từ internet và truyền cho PIC. Hiện tôi đang thắc mắc vấn đề này. PIC có một ngắt nhận RS232, #INT_RDA, nhưng tôi không biết khi nào thì ngắt này xảy ra, mỗi lần xảy ra nó nhận dữ liệu như thế nào, vì nếu PC truyền 6 số kiểu integer thì PIC nhận như thế nào, còn nếu PC truyền 1 biến chuỗi (ghép tất cả 6 biến kia lại ) thì PIC nhận như thế nào. và khi truyền thì nó truyền dữ liệu theo dạng nào. Nếu tôi truyền ngay số nguyên 14 thì PIC nhận là 0E? Ai biết về ngắt này thì giúp tôi 1 chút

#INT_RDA liên quan đến ngôn ngữ và trình biên dịch cụ thể (mà bạn chưa đề cập đến ở đây). Với PIC16, chỉ có một vectơ ngắt cho tất cả các ngắt, và bạn cần kiểm tra cờ ngắt tương ứng với sự kiện mà bạn cần xử lý (ở đây là cờ RCIF) trong chương trình xử lý ngắt chung đó. PIC16 sẽ nhận từng byte vào thanh ghi đệm, đây là thanh ghi đệm kép, có khả năng chứa được 2 byte trong khi byte thứ ba được dịch vào thanh ghi dịch. Nếu xử lý ngắt tốt, bạn hoàn toàn có thể nhận 6 integer. Khi truyền và nhận thì đều là mã nhị phân (có thể dài 8 hay 9 bit). Nếu truyền một byte có giá trị thập phân là 14 thì giá trị nhận được tại PIC sẽ là 14 thập phân hay 0E hexadecimal (nếu khác đi thì đâu có ý nghĩa gì nữa). Bạn chịu khó đọc phần 10 trong datasheet của PIC16F877A.

Thân,

anhct 17-12-2006 10:42 AM

Tôi cũng mới làm một chút về phần truyền thông thông qua cổng RS232. Tôi làm là: đo đa kênh sử dụng PIC6F877A và truyền thông lên máy tinh dùng giao thức MODBUS ASCII. Lập trình cho PIC dùng CCS. Trên máy tính tôi dùng VB để tạo giao diện và giao tiếp. Chương trình trên VB gửi yêu cầu xuống PIC là đọc mấy kênh và cụ thể là những kênh nào. Theo tôi thấy yêu cầu của bạn tạm thời chỉ cần 1 chiều truyền xuống từ máy tính xuống PIC. Tôi thực sự không hiểu kỹ lắm về ngắt của PIC nên không dám mạn đàm nhiều, có điều tôi đã làm và truyền khá tốt nên tôi có góp ý một chút như sau ( nếu bạn lập trình dùng CCS thì có thể tham khảo còn nếu không thì tôi cũng cứ đưa lên biết đâu sẽ có bạn đọc và góp ý cho mình ):
Bạn truyền từ máy tính xuống có thể truyền theo chuỗi ( tôi đã làm và truyền rất tốt, tôi truyền khoảng trên 20 ký tự ), số của bạn là số nguyên 6 chữ số bạn đổi ra dạng string rồi gửi ra cổng COM. Tôi không biết bạn truyền thông qua cổng COM sử dụng lớp gì, có lẽ là MSCOMM; còn tôi thường dùng CWSerial của MS Studio.
Còn dưới PIC bạn dùng ngắt nhận #INT_RDA; tôi không hiểu kỹ lắm đâu nhưng tôi làm và nghĩ rằng ( nếu không đúng các bác góp ý hộ nhé ) khi có ký tự truyền tới bộ đệm thì sẽ xảy ra ngắt.
- Có thể dùng hàm getc() để nhận từng ký tự rồi lưu lại thành chuỗi sau đó bạn dùng hàm atoi() chẳng hạn để chuyển sang số dạng integer.
- Cũng có thể dùng hàm gets() để nhận cả chuỗi nhưng khi truyền từ máy tính kết thúc khung phải có ký tự '\r' (13), để kết thúc chuỗi thì PIC mới nhận đủ chuỗi được.
- Nếu cẩn thận hơn bạn có thể kiểm tra bộ đệm dùng hàm kbhit(), cái này tôi cũng đã dùng thử.
Không biết khi tôi post bài này bạn đã làm xong chưa nhưng tôi cũng đưa đoạn code nhận có ngắt nhận #INT_RDA để bạn tham khảo và góp ý nhé.

anhct 17-12-2006 12:18 PM

Đoạn code dưới PIC để nhận chuỗi từ máy tính:
Code:

#int_RDA
RDA_isr()
{
  delay_us(10);
  ss= getc();
  if (ss==':')  index= 0;
  if (ss=='\n')
      {
        st_nhan[index++]= ss;
        st_nhan[index]= '\0';
        index= 0;
      }
      else
        st_nhan[index++]= ss;
  NGAT= 1;
}


anhct 17-12-2006 12:24 PM

Tôi truyền theo giao thức MODBUS ASCII nên khung truyền có dạng:
":" & "Khung can truyen " & "\n"
( Thực ra đây chưa phải khung chuẩn của MODBUS ASCII nhưng tôi chỉ gửi minh họa thôi ).
Có thể dùng khung giao thức khác tùy bạn. Có gì thì các bạn góp ý cho mình nhé. Đây chỉ là một cách nhận dữ liệu thôi còn nhiều cách khác nếu bạn nào muốn biết thì mình sẽ gửi thêm.

vietvuong 09-07-2007 06:08 PM

bạn anhct ơi, mình cũng đang làm và giao tiếp PIC 16F877A qua modbus. Bạn có thể cho mình xin địa chỉ email để khi nào có khó khăn mình hỏi bạn không. Rất mong nhận được hồi âm của bạn.

anhct 29-09-2007 10:44 PM

Trích:

Nguyên văn bởi vietvuong (Post 9941)
bạn anhct ơi, mình cũng đang làm và giao tiếp PIC 16F877A qua modbus. Bạn có thể cho mình xin địa chỉ email để khi nào có khó khăn mình hỏi bạn không. Rất mong nhận được hồi âm của bạn.

hi hi, tôi làm cái này từ năm ngoái lúc còn làm đồ án tốt nghiệp, giờ thì quên gần hết rùi. Nếu bạn cần tham khảo code cho PIC có thể liên hệ với tôi qua email cũng được, tôi sẽ gửi code cho bạn tham khảo.
Mail: anhct84@gmail.com

P/S: dạo này tôi ko lên diễn đàn mấy đâu, bạn nào quan tâm có thể liên hệ với tôi qua email, nếu tôi biết gì sẽ trao đổi hoặc post lại lên diễn đàn.

dinhbv_dkh 07-04-2008 02:35 AM

Giao diện Guide
 
Cho hỏi khi giao tiếp Rs232 mình có phải định dạng khung truyền dữ liệu từ giao diện không ? Giả sử truyền 4 bit , đầu tiên là D ..OK là kết thúc . Và quá trình nhận từ PIC lên cũng tương tự ??!! mình có sư dụng chương trình RS232 Communication của NG Hải Bắc, test với cổng COM thì được nhưng khi truyền thông PIC thì không thấy phản ứng gì ? Thế là sao nhỉ ?Làm với bác Gui này toát mồ hôi quá !

anhct 08-06-2008 05:47 PM

1 Attachment(s)
Trong thời gian qua có một số bạn có liên hệ với tôi để xin code tham khảo, do hiện nay tôi không còn làm trong lĩnh vực này nữa và thực sự cũng hơi bận nên đôi khi không thể reply sớm cho các bạn, tôi gửi kèm file source code của chương trình tôi viết cho bạn nào quan tâm có thể tham khảo.

anhct 08-06-2008 05:50 PM

Trích:

Nguyên văn bởi dinhbv_dkh (Post 15386)
Cho hỏi khi giao tiếp Rs232 mình có phải định dạng khung truyền dữ liệu từ giao diện không ? Giả sử truyền 4 bit , đầu tiên là D ..OK là kết thúc . Và quá trình nhận từ PIC lên cũng tương tự ??!! mình có sư dụng chương trình RS232 Communication của NG Hải Bắc, test với cổng COM thì được nhưng khi truyền thông PIC thì không thấy phản ứng gì ? Thế là sao nhỉ ?Làm với bác Gui này toát mồ hôi quá !

Định dạng khung truyền là như nào nhỉ? Tôi không hiểu rõ ý bạn lắm.
Theo tôi là thiết lập chế độ truyền: start, data, stop; truyền mấy byte data....
Nếu thiết lập trên máy tính truyền và nhận như nào: start 1 bit, data 7 bit, stop 1,5 bit chẳng hạn thì ở dưới phần cứng (PIC bạn cũng phải thiết lập y như vậy) thì mới giao tiếp được.
Tôi không biết rõ yêu cầu nên chỉ góp ý như vậy thôi :)

giang27t1 14-12-2008 12:02 PM

Mình cần một đoạn Code viết bằng VB6 cho việc giao tiếp giữa máy đọc mã vạch với PC

trieucn 14-12-2008 06:39 PM

Dùng CCS lập trình giao tiếp RS232 rất dễ. Tui đã làm thử qua rùi.
Với việc định nghĩa #use RS232 (...), PIC sẽ tự thêm các bit start, stop và VRC cho các bạn. Các bạn chỉ việc viết hàm chuyền và nhận byte. Thế là xong!
Trong CCS có hàm gets(), dùng để nhận một byte truyền đến từ chân RX trên VDK. Hàm này sẽ chờ cho đến khi có dữ liệu truyền đến và lấy dữ liệu. Khi sử dụng hàm này, VDK ko làm bất cứ việc gì khác (mình đã test thử). Vì vậy, để tránh hiện tượng này, tốt nhất là ta sử dụng ngắt #int_RDA. Khi có dữ liệu truyền đến sẽ sinh ra một ngắt. Cách sử dụng ngắt này, anh ANHCT đã cho các bạn code rùi, mình ko cần phải viết ra nữa. Tuy nhiên, có thể sửa code đó bằng việc bỏ đi hàm delay. Nếu sử dụng nhiều giao tiếp RS232 trên 1 VDK, bạn có thể dùng hàm kbhit(). Hàm này sẽ phát hiện xem có dữ liệu truyền đến hay ko. Cách sử dụng hàm này thì như sau:
if(kbhit())
{
xau[i]=gets();
i++;
///...........(các bạn tự thêm code cho mình nha)
}

Còn việc gửi dữ liệu đi, trong CCS có một hàm là putc(). Hàm này có tác dụng là gửi một chuỗi dữ liệu lên chân TX của PIC. Đế có thể truyền một xâu qua chân TX, ta viết một hàm truyền như sau:
void truyen(char c)
{
putc(c);
}
hàm trên chỉ truyền một ký tự lên chân TX. Để truyền một xâu, ta sử dụng hàm printf kết hợp với hàm truyen() dạng như sau:

string XAU;
......
printf(truyen,"%s",xau);

Còn việc tiếp theo là của các bạn. Chúc các bạn thành công!

Hard 15-12-2008 09:49 AM

Hi,
Việc truyền số liệu giữa PC và PIC tui cũng có làm vài lần, nhân tiện chia sẽ với các bác chút kinh nghiệm. Giao tiếp có 2 kiểu, một là truyền số nhị phân hai là truyền khung dữ liệu. Truyền số nhị phân đơn giản chỉ là gửi từng byte lên/xuống giữa PC và PIC, trong trường hợp này chúng ta cần phải biết ý nghĩa của từng byte để xử lý và phải truyền phản hồi lại để kiểm tra có lỗi xãy ra hay không. Ví dụ PC gửi ký tự 'A' xuống PIC, khi PIC nhận được thì gửi ngược lên PC, PC kiểm tra nếu đúng là ký tự 'A' vừa gửi thì có nghĩa là việc truyền thành công. Kiểu thứ 2 là truyền dạng khung, số liệu được đóng theo từng khung và gửi lên/xuống giữa PIC và PC. Mỗi khung bao gồm ký tự Bắt Đầu (báo bắt đầu khung), ký tự Nhận Dạng (chỉ thị là khung Lệnh điều khiển hay là khung Dữ liệu), tiếp theo là Kích Thước của số liệu (số byte dữ liệu trong khung), tiếp theo là Mã kiểm tra (thường là mã Checksum) và cuối cùng là ký tự Kết Thúc Khung. Khi PC/PIC nhận xong một khung thì sẽ xử lý và kiểm tra lỗi, nếu không có lỗi thì gửi phản hồi lại ký tự 'ACK' để báo cho phía gửi biết là truyền thành công, ngược lại gửi ký tự 'NOACK' để báo là có lỗi xảy ra trong quá trình truyền và yêu cầu truyền lại.
Tuỳ theo ứng dụng của các bác, kiểu truyền số liệu để chon phương pháp nào hiệu quả hơn. Chúc các bác sớm thành công.
Thân ái.

thuc101 26-03-2010 09:04 AM

cam on
 
Trích:

Nguyên văn bởi anhct (Post 6399)
Tôi truyền theo giao thức MODBUS ASCII nên khung truyền có dạng:
":" & "Khung can truyen " & "\n"
( Thực ra đây chưa phải khung chuẩn của MODBUS ASCII nhưng tôi chỉ gửi minh họa thôi ).
Có thể dùng khung giao thức khác tùy bạn. Có gì thì các bạn góp ý cho mình nhé. Đây chỉ là một cách nhận dữ liệu thôi còn nhiều cách khác nếu bạn nào muốn biết thì mình sẽ gửi thêm.








neu nhu vay bac cho tui hoi them mot chut nha:
nhận thì được rồi nhưng tui muốn hỏi thêm vè phàn gởi từ trên máy tinh xuống thì ta làm sao

chau_2007 27-03-2010 03:03 AM

Trích:

Nguyên văn bởi thuc101 (Post 34427)
neu nhu vay bac cho tui hoi them mot chut nha:
nhận thì được rồi nhưng tui muốn hỏi thêm vè phàn gởi từ trên máy tinh xuống thì ta làm sao

Thì viết trên máy tính chứ sao. Tùy ngôn ngữ chọn VB, C#, C++. Lời khuyên, đối với RS232, dùng C# là hay nhất.


Múi giờ GMT. Hiện tại là 04:38 PM.

Tên diễn đàn: vBulletin Version 3.8.11
Được sáng lập bởi Đoàn Hiệp.
Copyright © PIC Vietnam