เชเชจเซเชเชฐเชจเซเช เชฒเชพเชเชฌเชพ เชธเชฎเชฏ เชชเชนเซเชฒเชพ เชฌเชฆเชฒเชพเช เชเชฏเซเช เชเซ. เชเชจเซเชเชฐเชจเซเชเชจเชพ เชฎเซเชเซเชฏ เชชเซเชฐเซเชเซเชเซเชฒเซเชธเชฎเชพเชเชฅเซ เชเช - UDP เชจเซ เชเชชเชฏเซเช เชเชชเซเชฒเซเชเซเชถเชจเซ เชฆเซเชตเชพเชฐเชพ เชฎเชพเชคเซเชฐ เชกเซเชเชพเชเซเชฐเชพเชฎ เช
เชจเซ เชฌเซเชฐเซเชกเชเชพเชธเซเช เชชเชนเซเชเชเชพเชกเชตเชพ เชฎเชพเชเซ เช เชจเชนเซเช, เชชเชฃ เชจเซเชเชตเชฐเซเช เชจเซเชกเซเชธ เชตเชเซเชเซ "เชชเซเช
เชฐ-เชเซ-เชชเซเช
เชฐ" เชเชจเซเชเซเชถเชจเซเชธ เชชเซเชฐเชฆเชพเชจ เชเชฐเชตเชพ เชฎเชพเชเซ เชชเชฃ เชฅเชพเชฏ เชเซ. เชคเซเชจเซ เชธเชฐเชณ เชกเชฟเชเชพเชเชจเชจเซ เชฒเซเชงเซ, เช เชชเซเชฐเซเชเซเชเซเชฒเชจเชพ เช
เชเชพเช เชเชฃเชพ เชฌเชฟเชจเชเชฏเซเชเชฟเชค เชเชชเชฏเซเชเซ เชเซ, เชเซ เชเซ, เชชเซเชฐเซเชเซเชเซเชฒเชจเซ เชเชพเชฎเซเช, เชเซเชฎ เชเซ เชเซเชฐเชเชเซเชก เชกเชฟเชฒเชฟเชตเชฐเซเชจเซ เช
เชเชค, เชเซเชฏเชพเชเชฏ เช
เชฆเซเชถเซเชฏ เชฅเช เชจเชฅเซ. เช เชฒเซเช UDP เชชเชฐ เชฌเชพเชเชฏเชงเชฐเซเชเซเชค เชกเชฟเชฒเชฟเชตเชฐเซ เชชเซเชฐเซเชเซเชเซเชฒเชจเชพ เช
เชฎเชฒเซเชเชฐเชฃเชจเซเช เชตเชฐเซเชฃเชจ เชเชฐเซ เชเซ.
เช
เชจเซเชเซเชฐเชฎเชฃเชฟเชเชพ:
DisposeByTimeout เชชเชฆเซเชงเชคเชฟ เชชเซเชฐเซเชธเซเชธเชชเซเชเซเชเซเชธ เชชเชฆเซเชงเชคเชฟ เชฐเซเชธเซเชตเชชเซเชเซเช เชชเชฆเซเชงเชคเชฟ เชชเซเชเซเช เชชเชฆเซเชงเชคเชฟ เชฎเซเชเชฒเซ
เชชเชฐเชฟเชเชฏ
เชเชจเซเชเชฐเชจเซเชเชจเชพ เชฎเซเชณ เชเชฐเซเชเชฟเชเซเชเซเชเชฐเซ เชเช เชธเชฎเชพเชจ เชธเชฐเชจเชพเชฎเซเช เชธเซเชฅเชพเชจ เชงเชพเชฐเชฃ เชเชฐเซเชฏเซเช เชนเชคเซเช เชเซเชฎเชพเช เชฆเชฐเซเช เชจเซเชกเชจเซเช เชตเซเชถเซเชตเชฟเช เช
เชจเซ เช
เชจเชจเซเชฏ IP เชธเชฐเชจเชพเชฎเซเช เชนเชคเซเช เช
เชจเซ เชคเซ เช
เชจเซเชฏ เชจเซเชกเซเชธ เชธเชพเชฅเซ เชธเซเชงเซ เชธเชเชเชพเชฐ เชเชฐเซ เชถเชเซ เชเซ. เชนเชตเซ เชเชจเซเชเชฐเชจเซเช, เชตเชพเชธเซเชคเชตเชฎเชพเช, เชเช เช
เชฒเช เชเชฐเซเชเชฟเชเซเชเซเชเชฐ เชงเชฐเชพเชตเซ เชเซ - เชตเซเชถเซเชตเชฟเช IP เชธเชฐเชจเชพเชฎเชพเชเชจเซ เชเช เชตเชฟเชธเซเชคเชพเชฐ เช
เชจเซ NAT เชเชชเชเชฐเชฃเซเชจเซ เชชเชพเชเชณ เชเซเชชเชพเชฏเซเชฒเชพ เชเชพเชจเชเซ เชธเชฐเชจเชพเชฎเชพเชเชตเชพเชณเชพ เชเชฃเชพ เชตเชฟเชธเซเชคเชพเชฐเซ.
เชเชจเซเชเชฐเชจเซเชเชจเซเช เช เชเชฐเซเชเชฟเชเซเชเซเชเชฐ เชเซเชฒเชพเชฏเชเช-เชธเชฐเซเชตเชฐ เชเชฎเซเชฏเซเชจเชฟเชเซเชถเชจ เชฎเชพเชเซ เชชเซเชฐเชคเซเช เชฏเซเชเซเชฏ เชเซ, เชเซเชฏเชพเช เชเซเชฒเชพเชฏเชจเซเช เชเชพเชจเชเซ เชจเซเชเชตเชฐเซเชเชฎเชพเช เชนเซเช เชถเชเซ เชเซ, เช เชจเซ เชธเชฐเซเชตเชฐ เชชเชพเชธเซ เชตเซเชถเซเชตเชฟเช เชธเชฐเชจเชพเชฎเซเช เชเซ. เชชเชฐเชเชคเซ เชคเซ เชตเชเซเชเซ เชฌเซ เชเชพเชเช เซเชจเชพ เชธเซเชงเชพ เชเซเชกเชพเชฃ เชฎเชพเชเซ เชฎเซเชถเซเชเซเชฒเซเช เชเชญเซ เชเชฐเซ เชเซ เชตเชฟเชตเชฟเชง เชเชพเชจเชเซ เชจเซเชเชตเชฐเซเชเซเชธ. เชชเซเช เชฐ-เชเซ-เชชเซเช เชฐ เชเชชเซเชฒเซเชเซเชถเชจ เชเซเชฎ เชเซ เชตเซเชเชธ เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ (เชธเซเชเชพเชฏเชชเซ), เชเซเชฎเซเชชเซเชฏเซเชเชฐ (เชเซเชฎเชตเซเชฏเซเช เชฐ)เชฎเชพเช เชฐเซเชฎเซเช เชเชเซเชธเซเชธ เชฎเซเชณเชตเชตเซ เช เชฅเชตเชพ เชเชจเชฒเชพเชเชจ เชเซเชฎเชฟเชเช เชฎเชพเชเซ เชฌเซ เชจเซเชกเซเชธ เชตเชเซเชเซ เชธเซเชงเซ เชเซเชกเชพเชฃ เชฎเชนเชคเซเชตเชชเซเชฐเซเชฃ เชเซ.
เชตเชฟเชตเชฟเชง เชเชพเชจเชเซ เชจเซเชเชตเชฐเซเชเซเชธ เชชเชฐเชจเชพ เชเชชเชเชฐเชฃเซ เชตเชเซเชเซ เชชเซเช เชฐ-เชเซ-เชชเซเช เชฐ เชเชจเซเชเซเชถเชจ เชธเซเชฅเชพเชชเชฟเชค เชเชฐเชตเชพ เชฎเชพเชเซเชจเซ เชธเซเชฅเซ เช เชธเชฐเชเชพเชฐเช เชชเชฆเซเชงเชคเชฟเชเชฎเชพเชเชจเซ เชเชเชจเซ เชนเซเชฒ เชชเชเชเชฟเชเช เชเชนเซเชตเชพเชฎเชพเช เชเชตเซ เชเซ. เช เชคเชเชจเซเชเชจเซ เชเชชเชฏเซเช UDP เชชเซเชฐเซเชเซเชเซเชฒ เชชเชฐ เชเชงเชพเชฐเชฟเชค เชเชชเซเชฒเชฟเชเซเชถเชจเซ เชธเชพเชฅเซ เชธเชพเชฎเชพเชจเซเชฏ เชฐเซเชคเซ เชฅเชพเชฏ เชเซ.
เชชเชฐเชเชคเซ เชเซ เชคเชฎเชพเชฐเซ เชเชชเซเชฒเชฟเชเซเชถเชจเชจเซ เชกเซเชเชพเชจเซ เชฌเชพเชเชฏเชงเชฐเซเชเซเชค เชกเชฟเชฒเชฟเชตเชฐเซเชจเซ เชเชฐเซเชฐ เชนเซเชฏ, เชเชฆเชพเชนเชฐเชฃ เชคเชฐเซเชเซ, เชคเชฎเซ เชเชฎเซเชชเซเชฏเซเชเชฐเซเชธ เชตเชเซเชเซ เชซเชพเชเชฒเซ เชธเซเชฅเชพเชจเชพเชเชคเชฐเชฟเชค เชเชฐเซ เชเซ, เชคเซ UDP เชจเซ เชเชชเชฏเซเช เชเชฐเชตเชพเชฎเชพเช เชเชฃเซ เชฎเซเชถเซเชเซเชฒเซเช เชนเชถเซ เชเชพเชฐเชฃ เชเซ UDP เช เชเซเชฐเชเชเซเชเซเชค เชกเชฟเชฒเชฟเชตเชฐเซ เชชเซเชฐเซเชเซเชเซเชฒ เชจเชฅเซ เช เชจเซ TCPเชฅเซ เชตเชฟเชชเชฐเซเชค, เชเซเชฐเชฎเชฎเชพเช เชชเซเชเซเช เชกเชฟเชฒเชฟเชตเชฐเซ เชชเซเชฐเชฆเชพเชจ เชเชฐเชคเซเช เชจเชฅเซ. เชชเซเชฐเซเชเซเชเซเชฒ
เช เชเชฟเชธเซเชธเชพเชฎเชพเช, เชฌเชพเชเชฏเชงเชฐเซเชเซเชค เชชเซเชเซเช เชกเชฟเชฒเชฟเชตเชฐเซเชจเซ เชเชพเชคเชฐเซ เชเชฐเชตเชพ เชฎเชพเชเซ, เชเชชเซเชฒเซเชเซเชถเชจ เชฒเซเชฏเชฐ เชชเซเชฐเซเชเซเชเซเชฒเชจเซ เช เชฎเชฒ เชเชฐเชตเซ เชเชฐเซเชฐเซ เชเซ เชเซ เชเชฐเซเชฐเซ เชเชพเชฐเซเชฏเชเซเชทเชฎเชคเชพ เชชเซเชฐเชฆเชพเชจ เชเชฐเซ เชเซ เช เชจเซ UDP เชชเชฐ เชเชพเชฐเซเชฏ เชเชฐเซ เชเซ.
เชนเซเช เชนเชฎเชฃเชพเช เช เชจเซเชเชงเชตเชพ เชฎเชพเชเชเซ เชเซเช เชเซ เชตเชฟเชตเชฟเชง เชเชพเชจเชเซ เชจเซเชเชตเชฐเซเชเซเชธเชฎเชพเช เชจเซเชกเซเชธ เชตเชเซเชเซ TCP เชเชจเซเชเซเชถเชจ เชธเซเชฅเชพเชชเชฟเชค เชเชฐเชตเชพ เชฎเชพเชเซ TCP เชนเซเชฒ เชชเชเชเชฟเชเช เชเซเชเชจเชฟเช เชเซ, เชชเชฐเชเชคเซ เชเชฃเชพ NAT เชเชชเชเชฐเชฃเซ เชฆเซเชตเชพเชฐเชพ เชคเซเชจเชพ เชฎเชพเชเซ เชธเชฎเชฐเซเชฅเชจเชจเชพ เช เชญเชพเชตเชจเซ เชเชพเชฐเชฃเซ, เชคเซเชจเซ เชธเชพเชฎเชพเชจเซเชฏ เชฐเซเชคเซ เชเชจเซเชเซเช เชเชฐเชตเชพเชจเซ เชฎเซเชเซเชฏ เชฐเซเชค เชคเชฐเซเชเซ เชเชฃเชตเชพเชฎเชพเช เชเชตเชคเซ เชจเชฅเซ. เชเชตเชพ เชเชพเชเช เซ.
เช เชฒเซเชเชจเชพ เชฌเชพเชเซเชจเชพ เชญเชพเชเชฎเชพเช, เชนเซเช เชซเชเซเชค เชเซเชฐเชเชเซเชเซเชค เชกเชฟเชฒเชฟเชตเชฐเซ เชชเซเชฐเซเชเซเชเซเชฒเชจเชพ เช เชฎเชฒเซเชเชฐเชฃ เชชเชฐ เชงเซเชฏเชพเชจ เชเซเชจเซเชฆเซเชฐเชฟเชค เชเชฐเซเชถ. UDP เชนเซเชฒ เชชเชเชเชฟเชเช เชเซเชเชจเชฟเชเชจเชพ เช เชฎเชฒเซเชเชฐเชฃเชจเซเช เชตเชฐเซเชฃเชจ เชจเซเชเซเชจเชพ เชฒเซเชเซเชฎเชพเช เชเชฐเชตเชพเชฎเชพเช เชเชตเชถเซ.
เชชเซเชฐเซเชเซเชเซเชฒ เชเชฐเซเชฐเซเชฏเชพเชคเซ
- เชธเชเชพเชฐเชพเชคเซเชฎเช เชชเซเชฐเชคเชฟเชธเชพเชฆ เชชเชฆเซเชงเชคเชฟ (เชเชนเซเชตเชพเชคเชพ เชนเชเชพเชฐเชพเชคเซเชฎเช เชธเซเชตเซเชเซเชคเชฟ) เชฆเซเชตเชพเชฐเชพ เชตเชฟเชถเซเชตเชธเชจเซเชฏ เชชเซเชเซเช เชตเชฟเชคเชฐเชฃ
- เชฎเซเชเชพ เชกเซเชเชพเชจเชพ เชเชพเชฐเซเชฏเชเซเชทเชฎ เชเซเชฐเชพเชจเซเชธเชซเชฐเชจเซ เชเชฐเซเชฐเชฟเชฏเชพเชค, เชเชเชฒเซ เชเซ. เชชเซเชฐเซเชเซเชเซเชฒเซ เชฌเชฟเชจเชเชฐเซเชฐเซ เชชเซเชเซเช เชฐเชฟเชฒเซ เชเชฐเชตเชพเชจเซเช เชเชพเชณเชตเซเช เชเซเชเช
- เชกเชฟเชฒเชฟเชตเชฐเซ เชเชจเซเชซเชฐเซเชฎเซเชถเชจ เชฎเชฟเชเซเชจเชฟเชเชฎ ("เชถเซเชฆเซเชง" UDP เชชเซเชฐเซเชเซเชเซเชฒ เชคเชฐเซเชเซ เชเชพเชฐเซเชฏ เชเชฐเชตเชพเชจเซ เชเซเชทเชฎเชคเชพ) เชฐเชฆ เชเชฐเชตเชพเชจเซเช เชถเชเซเชฏ เชนเซเชตเซเช เชเซเชเช.
- เชฆเชฐเซเช เชธเชเชฆเซเชถเชจเซ เชชเซเชทเซเชเชฟ เชธเชพเชฅเซ, เชเชฆเซเชถ เชฎเซเชกเชจเซ เช เชฎเชฒเชฎเชพเช เชฎเซเชเชตเชพเชจเซ เชเซเชทเชฎเชคเชพ
- เชชเซเชฐเซเชเซเชเซเชฒ เชชเชฐ เชกเซเชเชพ เชเซเชฐเชพเชจเซเชธเชซเชฐเชจเซเช เชฎเซเชณเชญเซเชค เชเชเชฎ เชธเชเชฆเซเชถ เชนเซเชตเซเช เชเชตเชถเซเชฏเช เชเซ
เช เชเชตเชถเซเชฏเชเชคเชพเช เชฎเซเชเชพเชญเชพเชเซ เชเชฎเชพเช เชตเชฐเซเชฃเชตเซเชฒ เชตเชฟเชถเซเชตเชธเชจเซเชฏ เชกเซเชเชพ เชชเซเชฐเซเชเซเชเซเชฒ เชเชตเชถเซเชฏเชเชคเชพเช เชธเชพเชฅเซ เชธเซเชธเชเชเชค เชเซ
เช เชเชฐเซเชฐเชฟเชฏเชพเชคเซเชจเซ เชธเชฎเชเชตเชพ เชฎเชพเชเซ, เชเชพเชฒเซ TCP เช
เชจเซ UDP เชชเซเชฐเซเชเซเชเซเชฒเชจเซ เชเชชเชฏเซเช เชเชฐเซเชจเซ เชฌเซ เชจเซเชเชตเชฐเซเช เชจเซเชกเซเชธ เชตเชเซเชเซ เชกเซเชเชพ เชเซเชฐเชพเชจเซเชธเชซเชฐเชจเซ เชธเชฎเชฏ เชเซเชเช. เชเชพเชฒเซ เชฌเชเชจเซ เชเชฟเชธเซเชธเชพเชเชฎเชพเช เช
เชฎเชพเชฐเซ เชชเชพเชธเซ เชเช เชชเซเชเซเช เชเซเชตเชพเช เชเชถเซ.
TCP เชชเชฐ เชจเซเชจ-เชเชจเซเชเชฐเซเชเซเชเชฟเชต เชกเซเชเชพเชจเซเช เชเซเชฐเชพเชจเซเชธเชซเชฐ:
เชเซเชฎ เชคเชฎเซ เชกเชพเชฏเชพเชเซเชฐเชพเชฎเชฎเชพเชเชฅเซ เชเซเช เชถเชเซ เชเซ, เชชเซเชเซเช เชเซเชตเชพเช เชเชตเชพเชจเชพ เชเชฟเชธเซเชธเชพเชฎเชพเช, TCP เชเซเชตเชพเช เชเชฏเซเชฒเชพ เชชเซเชเซเชเชจเซ เชถเซเชงเซ เชเชพเชขเชถเซ เช
เชจเซ เชเซเชตเชพเชฏเซเชฒเชพ เชธเซเชเชฎเซเชจเซเชเชจเซ เชจเชเชฌเชฐ เชชเซเชเซเชจเซ เชฎเซเชเชฒเชจเชพเชฐเชจเซ เชคเซเชจเซ เชเชพเชฃ เชเชฐเชถเซ.
UDP เชชเซเชฐเซเชเซเชเซเชฒ เชฆเซเชตเชพเชฐเชพ เชกเซเชเชพ เชเซเชฐเชพเชจเซเชธเชซเชฐ:
UDP เชเซเช เชถเซเชงเชตเชพเชจเชพ เชเซเช เชชเชเชฒเชพเช เชฒเซเชคเซเช เชจเชฅเซ. UDP เชชเซเชฐเซเชเซเชเซเชฒเชฎเชพเช เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชญเซเชฒเซเชจเซเช เชจเชฟเชฏเชเชคเซเชฐเชฃ เชธเชเชชเซเชฐเซเชฃเชชเชฃเซ เชเชชเซเชฒเชฟเชเซเชถเชจเชจเซ เชเชตเชพเชฌเชฆเชพเชฐเซ เชเซ.
TCP เชชเซเชฐเซเชเซเชเซเชฒเชฎเชพเช เชญเซเชฒ เชถเซเชง เช เชเชจเซเชก เชจเซเชก เชธเชพเชฅเซ เชเชจเซเชเซเชถเชจ เชธเซเชฅเชพเชชเชฟเชค เชเชฐเซเชจเซ, เชคเซ เชเชจเซเชเซเชถเชจเชจเซ เชธเซเชฅเชฟเชคเชฟเชจเซ เชธเซเชเซเชฐ เชเชฐเซเชจเซ, เชฆเชฐเซเช เชชเซเชเซเช เชนเซเชกเชฐเชฎเชพเช เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซเชฒเซ เชฌเชพเชเชเซเชธเชจเซ เชธเชเชเซเชฏเชพ เชธเซเชเชตเซเชจเซ เช เชจเซ เชธเซเชตเซเชเซเชคเชฟ เชจเชเชฌเชฐเชจเซ เชเชชเชฏเซเช เชเชฐเซเชจเซ เชฐเชธเซเชฆเซเชจเซ เชธเซเชเชฟเชค เชเชฐเซเชจเซ เชชเซเชฐเชพเชชเซเชค เชฅเชพเชฏ เชเซ.
เชตเชงเซเชฎเชพเช, เชเชพเชฎเชเซเชฐเซ เชฌเชนเซเชคเชฐ เชฌเชจเชพเชตเชตเชพ เชฎเชพเชเซ (เชเชเชฒเซ โโโโเชเซ เชธเซเชตเซเชเซเชคเชฟ เชชเซเชฐเชพเชชเซเชค เชเชฐเซเชฏเชพ เชตเชฟเชจเชพ เชเช เชเชฐเชคเชพ เชตเชงเซ เชธเซเชเชฎเซเชจเซเช เชฎเซเชเชฒเซ), TCP เชชเซเชฐเซเชเซเชเซเชฒ เชเชนเซเชตเชพเชคเซ เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชตเชฟเชจเซเชกเซเชจเซ เชเชชเชฏเซเช เชเชฐเซ เชเซ - เชกเซเชเชพเชจเชพ เชฌเชพเชเชเชจเซ เชธเชเชเซเชฏเชพ เชเซ เชธเซเชเชฎเซเชจเซเชเชจเชพ เชชเซเชฐเซเชทเชเชจเซ เชชเซเชฐเชพเชชเซเชค เชฅเชตเชพเชจเซ เช เชชเซเชเซเชทเชพ เชเซ.
TCP เชชเซเชฐเซเชเซเชเซเชฒ เชตเชฟเชถเซ เชตเชงเซ เชฎเชพเชนเชฟเชคเซ เชฎเชพเชเซ, เชเซเช
เชเชชเชฐเชฅเซ, เชคเซ เชธเซเชชเชทเซเช เชเซ เชเซ UDP เชชเชฐ เชตเชฟเชถเซเชตเชธเชจเซเชฏ เชธเชเชฆเซเชถ เชตเชฟเชคเชฐเชฃ เชชเซเชฐเซเชเซเชเซเชฒ เชฌเชจเชพเชตเชตเชพ เชฎเชพเชเซ (เชคเซเชฏเชพเชฐเชฌเชพเชฆ เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP), เชคเซ TCP เชเซเชตเซ เช เชกเซเชเชพ เชเซเชฐเชพเชจเซเชธเชซเชฐ เชฎเชฟเชเซเชจเชฟเชเชฎเซเชธ เชฒเชพเชเซ เชเชฐเชตเชพ เชฎเชพเชเซ เชเชฐเซเชฐเซ เชเซ. เชเซเชฎ เชเซ:
- เชเชจเซเชเซเชถเชจ เชธเซเชฅเชฟเชคเชฟ เชธเชพเชเชตเซ
- เชธเซเชเชฎเซเชจเซเช เชจเชเชฌเชฐเชฟเชเชเชจเซ เชเชชเชฏเซเช เชเชฐเซ
- เชเชพเชธ เชชเซเชทเซเชเชฟเชเชฐเชฃ เชชเซเชเซเชเซเชจเซ เชเชชเชฏเซเช เชเชฐเซ
- เชชเซเชฐเซเชเซเชเซเชฒ เชฅเซเชฐเซเชชเซเช เชตเชงเชพเชฐเชตเชพ เชฎเชพเชเซ เชธเชฐเชณ เชตเชฟเชจเซเชกเซเชเชเช เชฎเชฟเชเซเชจเชฟเชเชฎเชจเซ เชเชชเชฏเซเช เชเชฐเซ
เชตเชงเซเชฎเชพเช, เชคเชฎเชพเชฐเซ เชเชฐเซเชฐ เชเซ:
- เชเชจเซเชเซเชถเชจ เชฎเชพเชเซ เชธเชเชธเชพเชงเชจเซ เชซเชพเชณเชตเชตเชพ เชฎเชพเชเซ, เชธเชเชฆเซเชถเชจเซ เชถเชฐเซเชเชคเชจเซ เชธเชเชเซเชค เชเชชเซ
- เชชเซเชฐเชพเชชเซเชค เชธเชเชฆเซเชถเชจเซ เช เชชเชธเซเชเซเชฐเซเชฎ เชเชชเซเชฒเชฟเชเซเชถเชจเชฎเชพเช เชชเชธเชพเชฐ เชเชฐเชตเชพ เช เชจเซ เชชเซเชฐเซเชเซเชเซเชฒ เชธเชเชธเชพเชงเชจเซ เชเซเชกเชตเชพ เชฎเชพเชเซ เชธเชเชฆเซเชถเชจเชพ เช เชเชคเชจเซ เชธเชเชเซเชค เชเชชเซ
- เชเชจเซเชเซเชถเชจ-เชตเชฟเชถเชฟเชทเซเช เชชเซเชฐเซเชเซเชเซเชฒเชจเซ "เชถเซเชฆเซเชง" UDP เชคเชฐเซเชเซ เชเชพเชฐเซเชฏ เชเชฐเชตเชพ เชฎเชพเชเซ เชกเชฟเชฒเชฟเชตเชฐเซ เชชเซเชทเซเชเชฟเชเชฐเชฃ เชชเชฆเซเชงเชคเชฟเชจเซ เช เชเซเชทเชฎ เชเชฐเชตเชพเชจเซ เชฎเชเชเซเชฐเซ เชเชชเซ
เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP เชนเซเชกเชฐ
เชฏเชพเชฆ เชเชฐเซ เชเซ UDP เชกเซเชเชพเชเซเชฐเชพเชฎ IP เชกเซเชเชพเชเซเชฐเชพเชฎเชฎเชพเช เชธเชฎเชพเชตเชฟเชทเซเช เชเซ. เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP เชชเซเชเซเช UDP เชกเซเชเชพเชเซเชฐเชพเชฎเชฎเชพเช เชฏเซเชเซเชฏ เชฐเซเชคเซ "เชเชตเชฐเชฟเชค" เชเซ.
เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP เชนเซเชกเชฐ เชเชจเซเชเซเชชเซเชธเซเชฏเซเชฒเซเชถเชจ:
เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP เชนเซเชกเชฐเชจเซ เชฐเชเชจเชพ เชเชเชฆเชฎ เชธเชฐเชณ เชเซ:
- เชซเซเชฒเซเชเซเชธ - เชชเซเชเซเช เชจเชฟเชฏเชเชคเซเชฐเชฃ เชซเซเชฒเซเชเซเชธ
- MessageType - เช เชชเชธเซเชเซเชฐเซเชฎ เชเชชเซเชฒเซเชเซเชถเชจเซ เชฆเซเชตเชพเชฐเชพ เชเซเชเซเชเชธ เชธเชเชฆเซเชถเชพเช เชชเชฐ เชธเชฌเซเชธเซเชเซเชฐเชพเชเชฌ เชเชฐเชตเชพ เชฎเชพเชเซ เชเชชเชฏเซเชเชฎเชพเช เชฒเซเชตเชพเชคเซ เชธเชเชฆเซเชถ เชชเซเชฐเชเชพเชฐ
- เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชเชเชกเซ - เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจเชจเซ เชธเชเชเซเชฏเชพ, เชชเซเชฐเชพเชชเซเชคเชเชฐเซเชคเชพเชจเชพ เชธเชฐเชจเชพเชฎเชพ เช เชจเซ เชชเซเชฐเซเช เชธเชพเชฅเซ, เชเซเชกเชพเชฃเชจเซ เช เชจเชจเซเชฏ เชฐเซเชคเซ เชเชณเชเซ เชเซ
- PacketNumber - เชชเซเชเซเช เชจเชเชฌเชฐ
- เชตเชฟเชเชฒเซเชชเซ - เชตเชงเชพเชฐเชพเชจเชพ เชชเซเชฐเซเชเซเชเซเชฒ เชตเชฟเชเชฒเซเชชเซ. เชชเซเชฐเชฅเชฎ เชชเซเชเซเชเชจเชพ เชเชฟเชธเซเชธเชพเชฎเชพเช, เชคเซเชจเซ เชเชชเชฏเซเช เชธเชเชฆเซเชถเชจเซเช เชเชฆ เชฆเชฐเซเชถเชพเชตเชตเชพ เชฎเชพเชเซ เชฅเชพเชฏ เชเซ
เชงเซเชตเช เชจเซเชเซ เชฎเซเชเชฌ เชเซ:
- เชซเชฐเซเชธเซเชเชชเซเชเซเช - เชธเชเชฆเซเชถเชจเซเช เชชเซเชฐเชฅเชฎ เชชเซเชเซเช
- NoAsk - เชธเชเชฆเซเชถเชจเซ เชธเชเซเชทเชฎ เชเชฐเชตเชพ เชฎเชพเชเซ เชธเซเชตเซเชเซเชคเชฟ เชชเชฆเซเชงเชคเชฟเชจเซ เชเชฐเซเชฐ เชจเชฅเซ
- เชฒเชพเชธเซเชเชชเซเชเซเช - เชธเชเชฆเซเชถเชจเซเช เชเซเชฒเซเชฒเซเช เชชเซเชเซเช
- RequestForPacket - เชชเซเชทเซเชเชฟ เชชเซเชเซเช เช เชฅเชตเชพ เชเซเชตเชพเชฏเซเชฒเชพ เชชเซเชเซเช เชฎเชพเชเซเชจเซ เชตเชฟเชจเชเชคเซ
เชชเซเชฐเซเชเซเชเซเชฒเชจเชพ เชธเชพเชฎเชพเชจเซเชฏ เชธเชฟเชฆเซเชงเชพเชเชคเซ
เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP เชฌเซ เชเชพเชเช เซ เชตเชเซเชเซ เชฌเชพเชเชฏเชงเชฐเซเชเซเชค เชธเชเชฆเซเชถเชพ เชชเซเชฐเชธเชพเชฐเชฃ เชชเชฐ เชเซเชจเซเชฆเซเชฐเชฟเชค เชนเซเชตเชพเชฅเซ, เชคเซ เชฌเซเชเซ เชฌเชพเชเซ เชธเชพเชฅเซ เชเซเชกเชพเชฃ เชธเซเชฅเชพเชชเชฟเชค เชเชฐเชตเชพเชฎเชพเช เชธเชเซเชทเชฎ เชนเซเชตเซเช เชเซเชเช. เชเชจเซเชเซเชถเชจ เชธเซเชฅเชพเชชเชฟเชค เชเชฐเชตเชพ เชฎเชพเชเซ, เชชเซเชฐเซเชทเช เชซเชฐเซเชธเซเชเชชเซเชเซเช เชซเซเชฒเซเช เชธเชพเชฅเซ เชเช เชชเซเชเซเช เชฎเซเชเชฒเซ เชเซ, เชเซเชจเซ เชชเซเชฐเชคเชฟเชธเชพเชฆ เช เชฐเซเชฅ เช เชฅเชถเซ เชเซ เชเซเชกเชพเชฃ เชธเซเชฅเชพเชชเชฟเชค เชฅเชฏเซเช เชเซ. เชฌเชงเชพ เชชเซเชฐเชคเชฟเชญเชพเชต เชชเซเชเซเชเซ, เช เชฅเชตเชพ, เช เชจเซเชฏ เชถเชฌเซเชฆเซเชฎเชพเช, เชธเซเชตเซเชเซเชคเชฟ เชชเซเชเซเชเซ, เชนเชเชฎเซเชถเชพ PacketNumber เชซเซเชฒเซเชกเชจเซเช เชฎเซเชฒเซเชฏ เชธเชซเชณเชคเชพเชชเซเชฐเซเชตเช เชชเซเชฐเชพเชชเซเชค เชฅเชฏเซเชฒเชพ เชชเซเชเซเชเซเชจเชพ เชธเซเชฅเซ เชฎเซเชเชพ PacketNumber เชฎเซเชฒเซเชฏ เชเชฐเชคเชพเช เชตเชงเซ เชเช เชชเชฐ เชธเซเช เชเชฐเซ เชเซ. เชฎเซเชเชฒเซเชฒ เชชเซเชฐเชฅเชฎ เชชเซเชเซเช เชฎเชพเชเซ เชตเชฟเชเชฒเซเชชเซ เชซเซเชฒเซเชก เช เชธเชเชฆเซเชถเชจเซเช เชเชฆ เชเซ.
เชเชจเซเชเซเชถเชจเชจเซ เชธเชฎเชพเชชเซเชค เชเชฐเชตเชพ เชฎเชพเชเซ เชธเชฎเชพเชจ เชชเชฆเซเชงเชคเชฟเชจเซ เชเชชเชฏเซเช เชฅเชพเชฏ เชเซ. LastPacket เชงเซเชตเช เชธเชเชฆเซเชถเชจเชพ เชเซเชฒเซเชฒเชพ เชชเซเชเซเช เชชเชฐ เชธเซเช เชเชฐเซเชฒ เชเซ. เชชเซเชฐเชคเชฟเชญเชพเชต เชชเซเชเซเชเชฎเชพเช เชเซเชฒเซเชฒเชพ เชชเซเชเซเชเชจเซ เชธเชเชเซเชฏเชพ + 1 เชนเซเชฏ เชเซ, เชเซเชจเซ เช
เชฐเซเชฅ เชชเซเชฐเชพเชชเซเชค เชเชฐเชจเชพเชฐ เชฌเชพเชเซ เชฎเชพเชเซ เชธเชเชฆเซเชถเชจเซ เชธเชซเชณ เชกเชฟเชฒเชฟเชตเชฐเซ เชฅเชพเชฏ เชเซ.
เชเชจเซเชเซเชถเชจ เชธเซเชฅเชพเชชเชจเชพ เช
เชจเซ เชธเชฎเชพเชชเซเชคเชฟ เชฐเซเชเชพเชเซเชคเชฟ:
เชเซเชฏเชพเชฐเซ เชเชจเซเชเซเชถเชจ เชธเซเชฅเชพเชชเชฟเชค เชฅเชพเชฏ เชเซ, เชคเซเชฏเชพเชฐเซ เชกเซเชเชพ เชเซเชฐเชพเชจเซเชธเชซเชฐ เชถเชฐเซ เชฅเชพเชฏ เชเซ. เชกเซเชเชพ เชชเซเชเซเชเซเชจเชพ เชฌเซเชฒเซเชเชฎเชพเช เชชเซเชฐเชธเชพเชฐเชฟเชค เชฅเชพเชฏ เชเซ. เชฆเชฐเซเช เชฌเซเชฒเซเช, เชเซเชฒเซเชฒเชพ เชเช เชธเชฟเชตเชพเชฏ, เชชเซเชเซเชเซเชจเซ เชจเชฟเชถเซเชเชฟเชค เชธเชเชเซเชฏเชพ เชงเชฐเชพเชตเซ เชเซ. เชคเซ เชชเซเชฐเชพเชชเซเชค/เชชเซเชฐเชธเชพเชฐเชฃ เชตเชฟเชจเซเชกเซ เชฎเชพเชช เชธเชฎเชพเชจ เชเซ. เชกเซเชเชพเชจเชพ เชเซเชฒเซเชฒเชพ เชฌเซเชฒเซเชเชฎเชพเช เชเชเชพ เชชเซเชเซเช เชนเซเช เชถเชเซ เชเซ. เชฆเชฐเซเช เชฌเซเชฒเซเช เชฎเซเชเชฒเซเชฏเชพ เชชเชเซ, เชฎเซเชเชฒเชจเชพเชฐ เชฌเชพเชเซ เชกเชฟเชฒเชฟเชตเชฐเซ เชเชจเซเชซเชฐเซเชฎเซเชถเชจเชจเซ เชฐเชพเชน เชเซเช เชเซ เช
เชฅเชตเชพ เชเซเชตเชพเชฏเซเชฒเชพ เชชเซเชเซเชเชจเซ เชซเชฐเซเชฅเซ เชกเชฟเชฒเชฟเชตเชฐ เชเชฐเชตเชพเชจเซ เชตเชฟเชจเชเชคเซเชจเซ เชฐเชพเชน เชเซเช เชเซ, เชชเซเชฐเชคเชฟเชธเชพเชฆเซ เชฎเซเชณเชตเชตเชพ เชฎเชพเชเซ เชฐเชฟเชธเชฟเชต/เชเซเชฐเชพเชจเซเชธเชฎเชฟเช เชตเชฟเชจเซเชกเซ เชเซเชฒเซเชฒเซ เชฐเชพเชเซเชจเซ. เชฌเซเชฒเซเช เชกเชฟเชฒเชฟเชตเชฐเซเชจเซ เชชเซเชทเซเชเชฟ เชชเซเชฐเชพเชชเซเชค เชเชฐเซเชฏเชพ เชชเชเซ, เชชเซเชฐเชพเชชเซเชค/เชเซเชฐเชพเชจเซเชธเชฎเชฟเช เชตเชฟเชจเซเชกเซ เชถเชฟเชซเซเช เชฅเชพเชฏ เชเซ เช
เชจเซ เชกเซเชเชพเชจเซ เชเชเชณเชจเซ เชฌเซเชฒเซเช เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซ เชเซ.
เชชเซเชฐเชพเชชเซเชค เชเชฐเชจเชพเชฐ เชฌเชพเชเซ เชชเซเชเซเชเซ เชฎเซเชณเชตเซ เชเซ. เชฆเชฐเซเช เชชเซเชเซเช เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชตเชฟเชจเซเชกเซเชจเซ เช
เชเชฆเชฐ เชเชตเซ เชเซ เชเซ เชเซเชฎ เชคเซ เชเซเชตเชพ เชฎเชพเชเซ เชคเชชเชพเชธเชตเชพเชฎเชพเช เชเชตเซ เชเซ. เชชเซเชเซเชเซ เช
เชจเซ เชกเซเชชเซเชฒเชฟเชเซเชเซเชธ เชเซ เชตเชฟเชจเซเชกเซเชฎเชพเช เชเชตเชคเชพ เชจเชฅเซ เชคเซ เชซเชฟเชฒเซเชเชฐ เชเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ. เชเชพเชฐเชฃ เชเซ เชเซ เชตเชฟเชจเซเชกเซเชจเซเช เชเชฆ เชจเชฟเชถเซเชเชฟเชค เชนเซเชฏ เช
เชจเซ เชชเซเชฐเชพเชชเซเชคเชเชฐเซเชคเชพ เช
เชจเซ เชชเซเชฐเซเชทเช เชฎเชพเชเซ เชธเชฎเชพเชจ เชนเซเชฏ, เชคเซ เชชเซเชเซเชเชจเชพ เชฌเซเชฒเซเชเชจเซ เชจเซเชเชถเชพเชจ เชตเชฟเชจเชพ เชชเชนเซเชเชเชพเชกเชตเชพเชจเชพ เชเชฟเชธเซเชธเชพเชฎเชพเช, เชตเชฟเชจเซเชกเซเชจเซ เชกเซเชเชพเชจเชพ เชเชเชฒเชพ เชฌเซเชฒเซเชเชจเชพ เชชเซเชเซเชเซ เชชเซเชฐเชพเชชเซเชค เชเชฐเชตเชพ เชฎเชพเชเซ เชเชธเซเชกเชตเชพเชฎเชพเช เชเชตเซ เชเซ เช
เชจเซ เชกเชฟเชฒเชฟเชตเชฐเซเชจเซ เชชเซเชทเซเชเชฟ เชฅเชพเชฏ เชเซ. เชฎเซเชเชฒเซเชฒ. เชเซ เชตเชฐเซเช เชเชพเชเชฎเชฐ เชฆเซเชตเชพเชฐเชพ เชจเชฟเชฐเซเชงเชพเชฐเชฟเชค เชธเชฎเชฏเชเชพเชณเชพเชจเซ เช
เชเชฆเชฐ เชตเชฟเชจเซเชกเซ เชญเชฐเชพเชฏ เชจเชนเซเช, เชคเซ เชเซเช เชถเชฐเซ เชเชฐเชตเชพเชฎเชพเช เชเชตเชถเซ เชเซ เชเซเชจเชพ เชชเชฐ เชชเซเชเซเชเซ เชตเชฟเชคเชฐเชฟเชค เชเชฐเชตเชพเชฎเชพเช เชเชตเซเชฏเชพ เชจเชฅเซ เช
เชจเซ เชชเซเชจเชเชกเชฟเชฒเชฟเชตเชฐเซ เชฎเชพเชเซเชจเซ เชตเชฟเชจเชเชคเซเช เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเชถเซ.
เชฐเซเชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชกเชพเชฏเชพเชเซเชฐเชพเชฎ:
เชธเชฎเชฏเชธเชฎเชพเชชเซเชคเชฟ เช
เชจเซ เชชเซเชฐเซเชเซเชเซเชฒ เชเชพเชเชฎเชฐ
เชเชจเซเชเซเชถเชจ เชธเซเชฅเชพเชชเชฟเชค เชเชฐเซ เชถเชเชพเชคเซเช เชจเชฅเซ เชคเซเชจเชพ เชเชฃเชพ เชเชพเชฐเชฃเซ เชเซ. เชเชฆเชพเชนเชฐเชฃ เชคเชฐเซเชเซ, เชเซ เชชเซเชฐเชพเชชเซเชค เชเชฐเชจเชพเชฐ เชชเชเซเชท เชเชซเชฒเชพเชเชจ เชนเซเชฏ. เช เชเชฟเชธเซเชธเชพเชฎเชพเช, เชเชจเซเชเซเชถเชจ เชธเซเชฅเชพเชชเชฟเชค เชเชฐเชตเชพเชจเซ เชชเซเชฐเชฏเชพเชธ เชเชฐเชคเซ เชตเชเชคเซ, เชธเชฎเชฏเชธเชฎเชพเชชเซเชคเชฟ เชฆเซเชตเชพเชฐเชพ เชเซเชกเชพเชฃ เชฌเชเชง เชฅเช เชเชถเซ. เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP เช เชฎเชฒเซเชเชฐเชฃ เชธเชฎเชฏเชธเชฎเชพเชชเซเชคเชฟ เชธเซเช เชเชฐเชตเชพ เชฎเชพเชเซ เชฌเซ เชเชพเชเชฎเชฐเชจเซ เชเชชเชฏเซเช เชเชฐเซ เชเซ. เชชเซเชฐเชฅเชฎ, เชเชพเชฐเซเชฏเชเชพเชฐเซ เชเชพเชเชฎเชฐเชจเซ เชเชชเชฏเซเช เชฐเชฟเชฎเซเช เชนเซเชธเซเช เชคเชฐเชซเชฅเซ เชชเซเชฐเชคเชฟเชธเชพเชฆเชจเซ เชฐเชพเชน เชเซเชตเชพ เชฎเชพเชเซ เชฅเชพเชฏ เชเซ. เชเซ เชคเซ เชชเซเชฐเซเชทเช เชฌเชพเชเซ เชชเชฐ เชซเชพเชฏเชฐ เชฅเชพเชฏ เชเซ, เชคเซ เชเซเชฒเซเชฒเซเช เชฎเซเชเชฒเซเชฒเซเช เชชเซเชเซเช เชซเชฐเซเชฅเซ เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซ เชเซ. เชเซ เชเชพเชเชฎเชฐ เชชเซเชฐเชพเชชเซเชคเชเชฐเซเชคเชพ เชชเชฐ เชธเชฎเชพเชชเซเชค เชฅเชพเชฏ เชเซ, เชคเซ เชชเชเซ เชเซเชตเชพเชฏเซเชฒเชพ เชชเซเชเซเชเซเชจเซ เชคเชชเชพเชธ เชเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ เช เชจเซ เชซเชฐเซเชฅเซ เชตเชฟเชคเชฐเชฃ เชฎเชพเชเซเชจเซ เชตเชฟเชจเชเชคเซเช เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซ เชเซ.
เชจเซเชกเซเชธ เชตเชเซเชเซเชจเชพ เชธเชเชเชพเชฐเชจเชพ เช เชญเชพเชตเชจเชพ เชเชฟเชธเซเชธเชพเชฎเชพเช เชเชจเซเชเซเชถเชจเชจเซ เชฌเชเชง เชเชฐเชตเชพ เชฎเชพเชเซ เชฌเซเชเชพ เชเชพเชเชฎเชฐเชจเซ เชเชฐเซเชฐ เชเซ. เชชเซเชฐเซเชทเช เชฌเชพเชเซ เชฎเชพเชเซ, เชคเซ เชเชพเชฐเซเชฏเชเชพเชฐเซ เชเชพเชเชฎเชฐ เชธเชฎเชพเชชเซเชค เชฅเชฏเชพ เชชเชเซ เชคเชฐเชค เช เชถเชฐเซ เชฅเชพเชฏ เชเซ, เช เชจเซ เชฐเชฟเชฎเซเช เชจเซเชก เชคเชฐเชซเชฅเซ เชชเซเชฐเชคเชฟเชธเชพเชฆเชจเซ เชฐเชพเชน เชเซเช เชเซ. เชเซ เชจเชฟเชฐเซเชฆเชฟเชทเซเช เชธเชฎเชฏเชเชพเชณเชพเชฎเชพเช เชเซเช เชชเซเชฐเชคเชฟเชธเชพเชฆ เชจ เชฎเชณเซ, เชคเซ เชเชจเซเชเซเชถเชจ เชธเชฎเชพเชชเซเชค เชเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ เช เชจเซ เชธเชเชธเชพเชงเชจเซ เชฌเชนเชพเชฐ เชชเชพเชกเชตเชพเชฎเชพเช เชเชตเซ เชเซ. เชฐเซเชธเซเชตเชฟเชเช เชฌเชพเชเซ เชฎเชพเชเซ, เชเชจเซเชเซเชถเชจ เชเซเชฒเซเช เชเชพเชเชฎเชฐ เชตเชฐเซเช เชเชพเชเชฎเชฐ เชฌเซ เชตเชพเชฐ เชธเชฎเชพเชชเซเชค เชฅเชฏเชพ เชชเชเซ เชถเชฐเซ เชฅเชพเชฏ เชเซ. เชเชจเซเชซเชฐเซเชฎเซเชถเชจ เชชเซเชเซเชเชจเซ เชเซเช เชธเชพเชฎเซ เชตเซเชฎเซ เชฒเซเชตเชพ เชฎเชพเชเซ เช เชเชฐเซเชฐเซ เชเซ. เชเซเชฏเชพเชฐเซ เชเชพเชเชฎเชฐ เชธเชฎเชพเชชเซเชค เชฅเชพเชฏ เชเซ, เชคเซเชฏเชพเชฐเซ เชเชจเซเชเซเชถเชจ เชชเชฃ เชธเชฎเชพเชชเซเชค เชฅเชพเชฏ เชเซ เช เชจเซ เชธเชเชธเชพเชงเชจเซ เชชเซเชฐเชเชพเชถเชฟเชค เชฅเชพเชฏ เชเซ.
เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชธเซเชเซเช เชกเชพเชฏเชพเชเซเชฐเชพเชฎ
เชชเซเชฐเซเชเซเชเซเชฒเชจเชพ เชธเชฟเชฆเซเชงเชพเชเชคเซ เชฎเชฐเซเชฏเชพเชฆเชฟเชค เชฐเชพเชเซเชฏ เชฎเชถเซเชจเชฎเชพเช เชฒเชพเชเซ เชเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ, เชเซเชฎเชพเชเชฅเซ เชฆเชฐเซเช เชฐเชพเชเซเชฏ เชชเซเชเซเช เชชเซเชฐเชเซเชฐเชฟเชฏเชพเชจเชพ เชเซเชเซเชเชธ เชคเชฐเซเช เชฎเชพเชเซ เชเชตเชพเชฌเชฆเชพเชฐ เชเซ.
เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP เชธเซเชเซเช เชกเชพเชฏเชพเชเซเชฐเชพเชฎ:
เชฌเชเชง - เชเชฐเซเชเชฐ เชเช เชฐเชพเชเซเชฏ เชจเชฅเซ, เชคเซ เชเชเซเชฎเซเชเชจ เชฎเชพเชเซ เชถเชฐเซเชเชค เช
เชจเซ เช
เชเชคเชฟเชฎ เชฌเชฟเชเชฆเซ เชเซ. เชฐเชพเชเซเชฏ เชฎเชพเชเซ เชฌเชเชง เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชเชเชเซเชฐเซเชฒ เชฌเซเชฒเซเช เชชเซเชฐเชพเชชเซเชค เชฅเชพเชฏ เชเซ, เชเซ, เช
เชธเซเชฎเซเชณ UDP เชธเชฐเซเชตเชฐเชจเซ เช
เชฎเชฒเชฎเชพเช เชฎเซเชเซเชจเซ, เชชเซเชเซเชเซเชจเซ เชฏเซเชเซเชฏ เชเซเชกเชพเชฃเซ เชชเชฐ เชซเซเชฐเชตเชฐเซเชก เชเชฐเซ เชเซ เช
เชจเซ เชธเซเชเซเช เชชเซเชฐเซเชธเซเชธเชฟเชเช เชถเชฐเซ เชเชฐเซ เชเซ.
FirstPacketSending - เชชเซเชฐเชพเชฐเชเชญเชฟเช เชธเซเชฅเชฟเชคเชฟ เชเซเชฎเชพเช เชธเชเชฆเซเชถ เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซ เชคเซเชฏเชพเชฐเซ เชเชเชเชเซเชเชเช เชเชจเซเชเซเชถเชจ เชนเซเชฏ เชเซ.
เช เชธเซเชฅเชฟเชคเชฟเชฎเชพเช, เชธเชพเชฎเชพเชจเซเชฏ เชธเชเชฆเซเชถเชพเช เชฎเชพเชเซ เชชเซเชฐเชฅเชฎ เชชเซเชเซเช เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซ เชเซ. เชชเซเชทเซเชเชฟเชเชฐเชฃ เชตเชฟเชจเชพเชจเชพ เชธเชเชฆเซเชถเชพเช เชฎเชพเชเซ, เช เชเชเชฎเชพเชคเซเชฐ เชฐเชพเชเซเชฏ เชเซ เชเซเชฏเชพเช เชธเชฎเชเซเชฐ เชธเชเชฆเซเชถ เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซ เชเซ.
เชธเชพเชฏเชเชฒ เชฎเซเชเชฒเซ - เชธเชเชฆเซเชถ เชชเซเชเซเชเชจเชพ เชชเซเชฐเชธเชพเชฐเชฃ เชฎเชพเชเซ เชเซเชฐเชพเชเชจเซเชก เชธเซเชเซเช.
เชฐเชพเชเซเชฏเชฎเชพเชเชฅเซ เชคเซเชฎเชพเช เชธเชเชเซเชฐเชฎเชฃ FirstPacketSending เชธเชเชฆเซเชถเชจเซเช เชชเซเชฐเชฅเชฎ เชชเซเชเซเช เชฎเซเชเชฒเซเชฏเชพ เชชเชเซ เชนเชพเชฅ เชงเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ. เชคเซ เช เชธเซเชฅเชฟเชคเชฟเชฎเชพเช เชเซ เชเซ เชคเชฎเชพเชฎ เชธเซเชตเซเชเซเชคเชฟเช เช เชจเซ เชชเซเชจเชเชชเซเชฐเชธเชพเชฐเชฃ เชฎเชพเชเซเชจเซ เชตเชฟเชจเชเชคเซเช เชเชตเซ เชเซ. เชคเซเชฎเชพเชเชฅเซ เชฌเชนเชพเชฐ เชจเซเชเชณเชตเซเช เชฌเซ เชเชฟเชธเซเชธเชพเชเชฎเชพเช เชถเชเซเชฏ เชเซ - เชธเชเชฆเซเชถเชจเชพ เชธเชซเชณ เชตเชฟเชคเชฐเชฃเชจเชพ เชเชฟเชธเซเชธเชพเชฎเชพเช เช เชฅเชตเชพ เชธเชฎเชฏ เชธเชฎเชพเชชเซเชค เชฅเชตเชพเชจเชพ เชเชฟเชธเซเชธเชพเชฎเชพเช.
เชซเชฐเซเชธเซเชเชชเซเชเซเช เชชเซเชฐเชพเชชเซเชค เชฅเชฏเซเช - เชธเชเชฆเซเชถ เชชเซเชฐเชพเชชเซเชคเชเชฐเซเชคเชพ เชฎเชพเชเซ เชชเซเชฐเชพเชฐเชเชญเชฟเช เชธเซเชฅเชฟเชคเชฟ.
เชคเซ เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจเชจเซ เชถเชฐเซเชเชคเชจเซ เชถเซเชฆเซเชงเชคเชพ เชคเชชเชพเชธเซ เชเซ, เชเชฐเซเชฐเซ เชฌเชเชงเชพเชฐเชฃ เชฌเชจเชพเชตเซ เชเซ เช เชจเซ เชชเซเชฐเชฅเชฎ เชชเซเชเซเชเชจเซ เชฐเชธเซเชฆ เชฎเซเชเชฒเซ เชเซ.
เชเชตเชพ เชธเชเชฆเซเชถ เชฎเชพเชเซ เชเซ เชเซเชฎเชพเช เชเช เช เชชเซเชเซเช เชนเซเชฏ เช เชจเซ เชกเชฟเชฒเชฟเชตเชฐเซเชจเชพ เชชเซเชฐเชพเชตเชพเชจเซ เชเชชเชฏเซเช เชเชฐเซเชฏเชพ เชตเชฟเชจเชพ เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซเชฏเซ เชนเซเชฏ, เช เชเชเชฎเชพเชคเซเชฐ เชฐเชพเชเซเชฏ เชเซ. เชเชตเชพ เชธเชเชฆเซเชถ เชชเชฐ เชชเซเชฐเชเซเชฐเชฟเชฏเชพ เชเชฐเซเชฏเชพ เชชเชเซ, เชเชจเซเชเซเชถเชจ เชฌเชเชง เชเซ.
เชเชธเซเชฎเซเชฌเชฒเชฟเชเช - เชธเชเชฆเซเชถ เชชเซเชเซเชเซ เชชเซเชฐเชพเชชเซเชค เชเชฐเชตเชพ เชฎเชพเชเซเชจเซ เชฎเซเชณเชญเซเชค เชธเซเชฅเชฟเชคเชฟ.
เชคเซ เช เชธเซเชฅเชพเชฏเซ เชธเชเชเซเชฐเชน เชฎเชพเชเซ เชชเซเชเซเชเซ เชฒเชเซ เชเซ, เชชเซเชเซเชเชจเซ เชเซเช เชคเชชเชพเชธเซ เชเซ, เชชเซเชเซเชเซเชจเชพ เชฌเซเชฒเซเช เช เชจเซ เชธเชฎเชเซเชฐ เชธเชเชฆเซเชถเชจเซ เชกเชฟเชฒเชฟเชตเชฐเซ เชฎเชพเชเซ เชธเซเชตเซเชเซเชคเชฟเช เชฎเซเชเชฒเซ เชเซ เช เชจเซ เชเซเชตเชพเชฏเซเชฒเชพ เชชเซเชเซเชเซเชจเซ เชชเซเชจเช เชกเชฟเชฒเชฟเชตเชฐเซ เชฎเชพเชเซ เชตเชฟเชจเชเชคเซเช เชฎเซเชเชฒเซ เชเซ. เชธเชฎเชเซเชฐ เชธเชเชฆเซเชถเชจเซ เชธเชซเชณ เชชเซเชฐเชพเชชเซเชคเชฟเชจเชพ เชเชฟเชธเซเชธเชพเชฎเชพเช, เชเชจเซเชเซเชถเชจ เชฐเชพเชเซเชฏเชฎเชพเช เชเชพเชฏ เชเซ เชชเซเชฐเซเชฃ, เช เชจเซเชฏเชฅเชพ, เชธเชฎเชฏเชธเชฎเชพเชชเซเชคเชฟ เชฌเชนเชพเชฐ เชจเซเชเชณเซ เชเชพเชฏ เชเซ.
เชชเซเชฐเซเชฃ - เชธเชฎเชเซเชฐ เชธเชเชฆเซเชถเชจเซ เชธเชซเชณเชคเชพเชชเซเชฐเซเชตเช เชชเซเชฐเชพเชชเซเชคเชฟเชจเชพ เชเชฟเชธเซเชธเชพเชฎเชพเช เชเชจเซเชเซเชถเชจ เชฌเชเชง เชเชฐเชตเซเช.
เช เชธเซเชฅเชฟเชคเชฟ เชธเชเชฆเซเชถเชจเซ เชเชธเซเชฎเซเชฌเชฒเซ เชฎเชพเชเซ เช เชจเซ เชคเซ เชเซเชธ เชฎเชพเชเซ เชเชฐเซเชฐเซ เชเซ เชเซเชฏเชพเชฐเซ เชชเซเชฐเซเชทเชเชจเชพ เชฎเชพเชฐเซเชเชฎเชพเช เชธเชเชฆเซเชถเชจเซ เชกเชฟเชฒเชฟเชตเชฐเซ เชชเซเชทเซเชเชฟ เชเซเชตเชพเช เชเช เชนเชคเซ. เช เชธเซเชฅเชฟเชคเชฟ เชธเชฎเชฏเชธเชฎเชพเชชเซเชคเชฟ เชฆเซเชตเชพเชฐเชพ เชฌเชนเชพเชฐ เชจเซเชเชณเซ เชเซ, เชชเชฐเชเชคเซ เชเชจเซเชเซเชถเชจ เชธเชซเชณเชคเชพเชชเซเชฐเซเชตเช เชฌเชเชง เชฎเชพเชจเชตเชพเชฎเชพเช เชเชตเซ เชเซ.
เชเซเชกเชฎเชพเช เชตเชงเซ เชเชเชกเซ. เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชเชเชเซเชฐเซเชฒ เชฏเซเชจเชฟเช
เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP เชจเชพ เชฎเซเชเซเชฏ เชเชเชเซเชฎเชพเชเชจเซเช เชเช เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชเชเชเซเชฐเซเชฒ เชฌเซเชฒเซเช เชเซ. เช เชฌเซเชฒเซเชเชจเซเช เชเชพเชฐเซเชฏ เชตเชฐเซเชคเชฎเชพเชจ เชเซเชกเชพเชฃเซ เช
เชจเซ เชธเชนเชพเชฏเช เชคเชคเซเชตเซเชจเซ เชธเชเชเซเชฐเชนเชฟเชค เชเชฐเชตเชพเชจเซเช เชเซ, เชเชตเชจเชพเชฐเชพ เชชเซเชเซเชเซเชจเซ เชธเชเชฌเชเชงเชฟเชค เชเซเชกเชพเชฃเซเชฎเชพเช เชตเชฟเชคเชฐเชฟเชค เชเชฐเชตเชพ, เชเชจเซเชเซเชถเชจเชฎเชพเช เชชเซเชเซเชเซ เชฎเซเชเชฒเชตเชพ เชฎเชพเชเซ เชเชจเซเชเชฐเชซเซเชธ เชชเซเชฐเชฆเชพเชจ เชเชฐเชตเชพ เช
เชจเซ เชชเซเชฐเซเชเซเชเซเชฒ API เชจเซ เช
เชฎเชฒเชฎเชพเช เชฎเซเชเชตเชพเชจเซเช เชเซ. เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชเชเชเซเชฐเซเชฒ เชฌเซเชฒเซเช UDP เชฒเซเชฏเชฐเชฎเชพเชเชฅเซ เชชเซเชเซเชเซ เชฎเซเชณเชตเซ เชเซ เช
เชจเซ เชคเซเชจเซ เชชเซเชฐเซเชธเซเชธเชฟเชเช เชฎเชพเชเซ เชธเซเชเซเช เชฎเชถเซเชจเชจเซ เชซเซเชฐเชตเชฐเซเชก เชเชฐเซ เชเซ. เชชเซเชเซเชเซ เชชเซเชฐเชพเชชเซเชค เชเชฐเชตเชพ เชฎเชพเชเซ, เชคเซ เช
เชธเซเชฎเซเชณ UDP เชธเชฐเซเชตเชฐเชจเซ เชฒเชพเชเซ เชเชฐเซ เชเซ.
ReliableUdpConnectionControlBlock เชตเชฐเซเชเชจเชพ เชเซเชเชฒเชพเช เชธเชญเซเชฏเซ:
internal class ReliableUdpConnectionControlBlock : IDisposable
{
// ะผะฐััะธะฒ ะฑะฐะนั ะดะปั ัะบะฐะทะฐะฝะฝะพะณะพ ะบะปััะฐ. ะัะฟะพะปัะทัะตััั ะดะปั ัะฑะพัะบะธ ะฒั
ะพะดััะธั
ัะพะพะฑัะตะฝะธะน
public ConcurrentDictionary<Tuple<EndPoint, Int32>, byte[]> IncomingStreams { get; private set;}
// ะผะฐััะธะฒ ะฑะฐะนั ะดะปั ัะบะฐะทะฐะฝะฝะพะณะพ ะบะปััะฐ. ะัะฟะพะปัะทัะตััั ะดะปั ะพัะฟัะฐะฒะบะธ ะธัั
ะพะดััะธั
ัะพะพะฑัะตะฝะธะน.
public ConcurrentDictionary<Tuple<EndPoint, Int32>, byte[]> OutcomingStreams { get; private set; }
// connection record ะดะปั ัะบะฐะทะฐะฝะฝะพะณะพ ะบะปััะฐ.
private readonly ConcurrentDictionary<Tuple<EndPoint, Int32>, ReliableUdpConnectionRecord> m_listOfHandlers;
// ัะฟะธัะพะบ ะฟะพะดะฟะธััะธะบะพะฒ ะฝะฐ ัะพะพะฑัะตะฝะธั.
private readonly List<ReliableUdpSubscribeObject> m_subscribers;
// ะปะพะบะฐะปัะฝัะน ัะพะบะตั
private Socket m_socketIn;
// ะฟะพัั ะดะปั ะฒั
ะพะดััะธั
ัะพะพะฑัะตะฝะธะน
private int m_port;
// ะปะพะบะฐะปัะฝัะน IP ะฐะดัะตั
private IPAddress m_ipAddress;
// ะปะพะบะฐะปัะฝะฐั ะบะพะฝะตัะฝะฐั ัะพัะบะฐ
public IPEndPoint LocalEndpoint { get; private set; }
// ะบะพะปะปะตะบัะธั ะฟัะตะดะฒะฐัะธัะตะปัะฝะพ ะธะฝะธัะธะฐะปะธะทะธัะพะฒะฐะฝะฝัั
// ัะพััะพัะฝะธะน ะบะพะฝะตัะฝะพะณะพ ะฐะฒัะพะผะฐัะฐ
public StatesCollection States { get; private set; }
// ะณะตะฝะตัะฐัะพั ัะปััะฐะนะฝัั
ัะธัะตะป. ะัะฟะพะปัะทัะตััั ะดะปั ัะพะทะดะฐะฝะธั TransmissionId
private readonly RNGCryptoServiceProvider m_randomCrypto;
//...
}
เช เชธเซเชฎเซเชณ UDP เชธเชฐเซเชตเชฐเชจเซเช เช เชฎเชฒเซเชเชฐเชฃ:
private void Receive()
{
EndPoint connectedClient = new IPEndPoint(IPAddress.Any, 0);
// ัะพะทะดะฐะตะผ ะฝะพะฒัะน ะฑััะตั, ะดะปั ะบะฐะถะดะพะณะพ socket.BeginReceiveFrom
byte[] buffer = new byte[DefaultMaxPacketSize + ReliableUdpHeader.Length];
// ะฟะตัะตะดะฐะตะผ ะฑััะตั ะฒ ะบะฐัะตััะฒะต ะฟะฐัะฐะผะตััะฐ ะดะปั ะฐัะธะฝั
ัะพะฝะฝะพะณะพ ะผะตัะพะดะฐ
this.m_socketIn.BeginReceiveFrom(buffer, 0, buffer.Length, SocketFlags.None, ref connectedClient, EndReceive, buffer);
}
private void EndReceive(IAsyncResult ar)
{
EndPoint connectedClient = new IPEndPoint(IPAddress.Any, 0);
int bytesRead = this.m_socketIn.EndReceiveFrom(ar, ref connectedClient);
//ะฟะฐะบะตั ะฟะพะปััะตะฝ, ะณะพัะพะฒั ะฟัะธะฝะธะผะฐัั ัะปะตะดัััะธะน
Receive();
// ั.ะบ. ะฟัะพััะตะนัะธะน ัะฟะพัะพะฑ ัะตัะธัั ะฒะพะฟัะพั ั ะฑััะตัะพะผ - ะฟะพะปััะธัั ัััะปะบั ะฝะฐ ะฝะตะณะพ
// ะธะท IAsyncResult.AsyncState
byte[] bytes = ((byte[]) ar.AsyncState).Slice(0, bytesRead);
// ะฟะพะปััะฐะตะผ ะทะฐะณะพะปะพะฒะพะบ ะฟะฐะบะตัะฐ
ReliableUdpHeader header;
if (!ReliableUdpStateTools.ReadReliableUdpHeader(bytes, out header))
{
// ะฟัะธัะตะป ะฝะตะบะพััะตะบัะฝัะน ะฟะฐะบะตั - ะพัะฑัะฐััะฒะฐะตะผ ะตะณะพ
return;
}
// ะบะพะฝััััะธััะตะผ ะบะปัั ะดะปั ะพะฟัะตะดะตะปะตะฝะธั connection recordโะฐ ะดะปั ะฟะฐะบะตัะฐ
Tuple<EndPoint, Int32> key = new Tuple<EndPoint, Int32>(connectedClient, header.TransmissionId);
// ะฟะพะปััะฐะตะผ ัััะตััะฒััััั connection record ะธะปะธ ัะพะทะดะฐะตะผ ะฝะพะฒัั
ReliableUdpConnectionRecord record = m_listOfHandlers.GetOrAdd(key, new ReliableUdpConnectionRecord(key, this, header.ReliableUdpMessageType));
// ะทะฐะฟััะบะฐะตะผ ะฟะฐะบะตั ะฒ ะพะฑัะฐะฑะพัะบั ะฒ ะบะพะฝะตัะฝัะน ะฐะฒัะพะผะฐั
record.State.ReceivePacket(record, header, bytes);
}
เชฆเชฐเซเช เชธเชเชฆเซเชถ เชเซเชฐเชพเชจเซเชธเชซเชฐ เชฎเชพเชเซ, เชเช เชฎเชพเชณเชเซเช เชฌเชจเชพเชตเชตเชพเชฎเชพเช เชเชตเซ เชเซ เชเซเชฎเชพเช เชเชจเซเชเซเชถเชจ เชตเชฟเชถเซเชจเซ เชฎเชพเชนเชฟเชคเซ เชนเซเชฏ เชเซ. เชเชตเซ เชฐเชเชจเชพ เชเชนเซเชตเชพเชฎเชพเช เชเชตเซ เชเซ เชเชจเซเชเซเชถเชจ เชฐเซเชเซเชฐเซเชก.
ReliableUdpConnectionRecord เชตเชฐเซเชเชจเชพ เชเซเชเชฒเชพเช เชธเชญเซเชฏเซ:
internal class ReliableUdpConnectionRecord : IDisposable
{
// ะผะฐััะธะฒ ะฑะฐะนั ั ัะพะพะฑัะตะฝะธะตะผ
public byte[] IncomingStream { get; set; }
// ัััะปะบะฐ ะฝะฐ ัะพััะพัะฝะธะต ะบะพะฝะตัะฝะพะณะพ ะฐะฒัะพะผะฐัะฐ
public ReliableUdpState State { get; set; }
// ะฟะฐัะฐ, ะพะดะฝะพะทะฝะฐัะฝะพ ะพะฟัะตะดะตะปัััะฐั connection record
// ะฒ ะฑะปะพะบะต ัะฟัะฐะฒะปะตะฝะธั ะฟะตัะตะดะฐัะตะน
public Tuple<EndPoint, Int32> Key { get; private set;}
// ะฝะธะถะฝัั ะณัะฐะฝะธัะฐ ะฟัะธะตะผะฝะพะณะพ ะพะบะฝะฐ
public int WindowLowerBound;
// ัะฐะทะผะตั ะพะบะฝะฐ ะฟะตัะตะดะฐัะธ
public readonly int WindowSize;
// ะฝะพะผะตั ะฟะฐะบะตัะฐ ะดะปั ะพัะฟัะฐะฒะบะธ
public int SndNext;
// ะบะพะปะธัะตััะฒะพ ะฟะฐะบะตัะพะฒ ะดะปั ะพัะฟัะฐะฒะบะธ
public int NumberOfPackets;
// ะฝะพะผะตั ะฟะตัะตะดะฐัะธ (ะธะผะตะฝะฝะพ ะพะฝ ะธ ะตััั ะฒัะพัะฐั ัะฐััั Tuple)
// ะดะปั ะบะฐะถะดะพะณะพ ัะพะพะฑัะตะฝะธั ัะฒะพะน
public readonly Int32 TransmissionId;
// ัะดะฐะปะตะฝะฝัะน IP endpoint โ ัะพะฑััะฒะตะฝะฝะพ ะฟะพะปััะฐัะตะปั ัะพะพะฑัะตะฝะธั
public readonly IPEndPoint RemoteClient;
// ัะฐะทะผะตั ะฟะฐะบะตัะฐ, ะฒะพ ะธะทะฑะตะถะฐะฝะธะต ััะฐะณะผะตะฝัะฐัะธะธ ะฝะฐ IP ััะพะฒะฝะต
// ะฝะต ะดะพะปะถะตะฝ ะฟัะตะฒััะฐัั MTU โ (IP.Header + UDP.Header + RelaibleUDP.Header)
public readonly int BufferSize;
// ะฑะปะพะบ ัะฟัะฐะฒะปะตะฝะธั ะฟะตัะตะดะฐัะตะน
public readonly ReliableUdpConnectionControlBlock Tcb;
// ะธะฝะบะฐะฟััะปะธััะตั ัะตะทัะปััะฐัั ะฐัะธะฝั
ัะพะฝะฝะพะน ะพะฟะตัะฐัะธะธ ะดะปั BeginSendMessage/EndSendMessage
public readonly AsyncResultSendMessage AsyncResult;
// ะฝะต ะพัะฟัะฐะฒะปััั ะฟะฐะบะตัั ะฟะพะดัะฒะตัะถะดะตะฝะธั
public bool IsNoAnswerNeeded;
// ะฟะพัะปะตะดะฝะธะน ะบะพััะตะบัะฝะพ ะฟะพะปััะตะฝะฝัะน ะฟะฐะบะตั (ะฒัะตะณะดะฐ ัััะฐะฝะฐะฒะปะธะฒะฐะตััั ะฒ ะฝะฐะธะฑะพะปััะธะน ะฝะพะผะตั)
public int RcvCurrent;
// ะผะฐััะธะฒ ั ะฝะพะผะตัะฐะผะธ ะฟะพัะตััะฝะฝัั
ะฟะฐะบะตัะพะฒ
public int[] LostPackets { get; private set; }
// ะฟัะธัะตะป ะปะธ ะฟะพัะปะตะดะฝะธะน ะฟะฐะบะตั. ะัะฟะพะปัะทัะตััั ะบะฐะบ bool.
public int IsLastPacketReceived = 0;
//...
}
เชเซเชกเชฎเชพเช เชตเชงเซ เชเชเชกเซ. เชฐเชพเชเซเชฏเซ
เชฐเชพเชเซเชฏเซ เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP เชชเซเชฐเซเชเซเชเซเชฒเชจเชพ เชฐเชพเชเซเชฏ เชฎเชถเซเชจเชจเซ เช เชฎเชฒ เชเชฐเซ เชเซ, เชเซเชฏเชพเช เชชเซเชเซเชเซเชจเซ เชฎเซเชเซเชฏ เชชเซเชฐเชเซเชฐเชฟเชฏเชพ เชฅเชพเชฏ เชเซ. เช เชฎเซเชฐเซเชค เชตเชฐเซเช ReliableUdpState เชฐเชพเชเซเชฏ เชฎเชพเชเซ เชเชจเซเชเชฐเชซเซเชธ เชชเซเชฐเชฆเชพเชจ เชเชฐเซ เชเซ:
เชชเซเชฐเซเชเซเชเซเชฒเชจเซ เชธเชฎเชเซเชฐ เชคเชฐเซเช เชเชชเชฐ เชชเซเชฐเชธเซเชคเซเชค เชตเชฐเซเชเซ เชฆเซเชตเชพเชฐเชพ เช
เชฎเชฒเชฎเชพเช เชฎเซเชเชตเชพเชฎเชพเช เชเชตเซ เชเซ, เชเช เชธเชนเชพเชฏเช เชตเชฐเซเช เชธเชพเชฅเซ เชเซ เชธเซเชฅเชฟเชฐ เชชเชฆเซเชงเชคเชฟเช เชชเซเชฐเชฆเชพเชจ เชเชฐเซ เชเซ, เชเซเชฎ เชเซ, เชเชจเซเชเซเชถเชจ เชฐเซเชเซเชฐเซเชกเชฎเชพเชเชฅเซ ReliableUdp เชนเซเชกเชฐเชจเซเช เชจเชฟเชฐเซเชฎเชพเชฃ.
เชเชเชณ, เช เชฎเซ เชเชจเซเชเชฐเชซเซเชธ เชชเชฆเซเชงเชคเชฟเชเชจเชพ เช เชฎเชฒเซเชเชฐเชฃ เชตเชฟเชถเซ เชตเชฟเชเชคเชตเชพเชฐ เชตเชฟเชเชพเชฐเชฃเชพ เชเชฐเซเชถเซเช เชเซ เชชเซเชฐเซเชเซเชเซเชฒเชจเชพ เชฎเซเชณเชญเซเชค เช เชฒเซเชเซเชฐเชฟเชงเชฎเซเชธเชจเซ เชจเชฟเชฐเซเชงเชพเชฐเชฟเชค เชเชฐเซ เชเซ.
DisposeByTimeout เชชเชฆเซเชงเชคเชฟ
DisposeByTimeout เชชเชฆเซเชงเชคเชฟ เชธเชฎเชฏเชธเชฎเชพเชชเซเชคเชฟ เชชเชเซ เชเชจเซเชเซเชถเชจ เชธเชเชธเชพเชงเชจเซ เชเซเชกเชตเชพ เชฎเชพเชเซ เช
เชจเซ เชธเชซเชณ/เช
เชธเชซเชณ เชธเชเชฆเซเชถ เชกเชฟเชฒเชฟเชตเชฐเซเชจเซ เชธเชเชเซเชค เชเชชเชตเชพ เชฎเชพเชเซ เชเชตเชพเชฌเชฆเชพเชฐ เชเซ.
ReliableUdpState.DisposeByTimeout:
protected virtual void DisposeByTimeout(object record)
{
ReliableUdpConnectionRecord connectionRecord = (ReliableUdpConnectionRecord) record;
if (record.AsyncResult != null)
{
connectionRecord.AsyncResult.SetAsCompleted(false);
}
connectionRecord.Dispose();
}
เชคเซ เชฎเชพเชคเซเชฐ เชฐเชพเชเซเชฏเชฎเชพเช เชเชตเชฐเชฐเชพเชเชก เชเซ เชชเซเชฐเซเชฃ.
เชชเซเชฐเซเชฃ เชฅเชฏเซเช.DisposeByTimeout:
protected override void DisposeByTimeout(object record)
{
ReliableUdpConnectionRecord connectionRecord = (ReliableUdpConnectionRecord) record;
// ัะพะพะฑัะฐะตะผ ะพะฑ ััะฟะตัะฝะพะผ ะฟะพะปััะตะฝะธะธ ัะพะพะฑัะตะฝะธั
SetAsCompleted(connectionRecord);
}
เชชเซเชฐเซเชธเซเชธเชชเซเชเซเชเซเชธ เชชเชฆเซเชงเชคเชฟ
ProcessPackets เชชเชฆเซเชงเชคเชฟ เชชเซเชเซเช เช เชฅเชตเชพ เชชเซเชเซเชเซเชจเซ เชตเชงเชพเชฐเชพเชจเซ เชชเซเชฐเชเซเชฐเชฟเชฏเชพ เชฎเชพเชเซ เชเชตเชพเชฌเชฆเชพเชฐ เชเซ. เชธเซเชงเชพ เช เชฅเชตเชพ เชชเซเชเซเช เชฐเชพเชน เชเชพเชเชฎเชฐ เชฆเซเชตเชพเชฐเชพ เชเซเชฒ เชเชฐเซ.
เชธเชเซเชทเชฎ เชเชธเซเชฎเซเชฌเชฒเชฟเชเช เชชเชฆเซเชงเชคเชฟ เชเชตเชฐเชฐเชพเชเชก เชเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ เช
เชจเซ เชเซเชตเชพเชฏเซเชฒเชพ เชชเซเชเซเชเซ เชฎเชพเชเซ เชคเชชเชพเชธ เชเชฐเชตเชพ เช
เชจเซ เชฐเชพเชเซเชฏเชฎเชพเช เชธเชเชเซเชฐเชฎเชฃ เชฎเชพเชเซ เชเชตเชพเชฌเชฆเชพเชฐ เชเซ เชชเซเชฐเซเชฃ, เชเซเชฒเซเชฒเซเช เชชเซเชเซเช เชฎเซเชณเชตเชตเชพ เช
เชจเซ เชธเชซเชณ เชเซเช เชชเชพเชธ เชเชฐเชตเชพเชจเชพ เชเชฟเชธเซเชธเชพเชฎเชพเช
เชเชธเซเชฎเซเชฌเชฒเชฟเชเช.เชชเซเชฐเซเชธเซเชธ เชชเซเชเซเชเซเชธ:
public override void ProcessPackets(ReliableUdpConnectionRecord connectionRecord)
{
if (connectionRecord.IsDone != 0)
return;
if (!ReliableUdpStateTools.CheckForNoPacketLoss(connectionRecord, connectionRecord.IsLastPacketReceived != 0))
{
// ะตััั ะฟะพัะตััะฝะฝัะต ะฟะฐะบะตัั, ะพัััะปะฐะตะผ ะทะฐะฟัะพัั ะฝะฐ ะฝะธั
foreach (int seqNum in connectionRecord.LostPackets)
{
if (seqNum != 0)
{
ReliableUdpStateTools.SendAskForLostPacket(connectionRecord, seqNum);
}
}
// ัััะฐะฝะฐะฒะปะธะฒะฐะตะผ ัะฐะนะผะตั ะฒะพ ะฒัะพัะพะน ัะฐะท, ะดะปั ะฟะพะฒัะพัะฝะพะน ะฟะพะฟััะบะธ ะฟะตัะตะดะฐัะธ
if (!connectionRecord.TimerSecondTry)
{
connectionRecord.WaitForPacketsTimer.Change(connectionRecord.ShortTimerPeriod, -1);
connectionRecord.TimerSecondTry = true;
return;
}
// ะตัะปะธ ะฟะพัะปะต ะดะฒัั
ะฟะพะฟััะพะบ ััะฐะฑะฐััะฒะฐะฝะธะน WaitForPacketTimer
// ะฝะต ัะดะฐะปะพัั ะฟะพะปััะธัั ะฟะฐะบะตัั - ะทะฐะฟััะบะฐะตะผ ัะฐะนะผะตั ะทะฐะฒะตััะตะฝะธั ัะพะตะดะธะฝะตะฝะธั
StartCloseWaitTimer(connectionRecord);
}
else if (connectionRecord.IsLastPacketReceived != 0)
// ััะฟะตัะฝะฐั ะฟัะพะฒะตัะบะฐ
{
// ะฒัััะปะฐะตะผ ะฟะพะดัะฒะตัะถะดะตะฝะธะต ะพ ะฟะพะปััะตะฝะธะธ ะฑะปะพะบะฐ ะดะฐะฝะฝัั
ReliableUdpStateTools.SendAcknowledgePacket(connectionRecord);
connectionRecord.State = connectionRecord.Tcb.States.Completed;
connectionRecord.State.ProcessPackets(connectionRecord);
// ะฒะผะตััะพ ะผะพะผะตะฝัะฐะปัะฝะพะน ัะตะฐะปะธะทะฐัะธะธ ัะตััััะพะฒ
// ะทะฐะฟััะบะฐะตะผ ัะฐะนะผะตั, ะฝะฐ ัะปััะฐะน, ะตัะปะธ
// ะตัะปะธ ะฟะพัะปะตะดะฝะธะน ack ะฝะต ะดะพะนะดะตั ะดะพ ะพัะฟัะฐะฒะธัะตะปั ะธ ะพะฝ ะทะฐะฟัะพัะธั ะตะณะพ ัะฝะพะฒะฐ.
// ะฟะพ ััะฐะฑะฐััะฒะฐะฝะธั ัะฐะนะผะตัะฐ - ัะตะฐะปะธะทัะตะผ ัะตััััั
// ะฒ ัะพััะพัะฝะธะธ Completed ะผะตัะพะด ัะฐะนะผะตัะฐ ะฟะตัะตะพะฟัะตะดะตะปะตะฝ
StartCloseWaitTimer(connectionRecord);
}
// ััะพ ัะปััะฐะน, ะบะพะณะดะฐ ack ะฝะฐ ะฑะปะพะบ ะฟะฐะบะตัะพะฒ ะฑัะป ะฟะพัะตััะฝ
else
{
if (!connectionRecord.TimerSecondTry)
{
ReliableUdpStateTools.SendAcknowledgePacket(connectionRecord);
connectionRecord.WaitForPacketsTimer.Change(connectionRecord.ShortTimerPeriod, -1);
connectionRecord.TimerSecondTry = true;
return;
}
// ะทะฐะฟััะบะฐะตะผ ัะฐะนะผะตั ะทะฐะฒะตััะตะฝะธั ัะพะตะดะธะฝะตะฝะธั
StartCloseWaitTimer(connectionRecord);
}
}
เชธเชเซเชทเชฎ เชธเชพเชฏเชเชฒ เชฎเซเชเชฒเซ เช เชชเชฆเซเชงเชคเชฟ เชซเชเซเชค เชเชพเชเชฎเชฐ เชชเชฐ เช เชฌเซเชฒเชพเชตเชตเชพเชฎเชพเช เชเชตเซ เชเซ, เช
เชจเซ เชคเซ เชเซเชฒเซเชฒเซ เชธเชเชฆเซเชถ เชซเชฐเซเชฅเซ เชฎเซเชเชฒเชตเชพ เชคเซเชฎเช เชเชจเซเชเซเชถเชจ เชเซเชฒเซเช เชเชพเชเชฎเชฐเชจเซ เชธเชเซเชทเชฎ เชเชฐเชตเชพ เชฎเชพเชเซ เชเชตเชพเชฌเชฆเชพเชฐ เชเซ.
SendingCycle.ProcessPackets:
public override void ProcessPackets(ReliableUdpConnectionRecord connectionRecord)
{
if (connectionRecord.IsDone != 0)
return;
// ะพัะฟัะฐะฒะปัะตะผ ะฟะพะฒัะพัะฝะพ ะฟะพัะปะตะดะฝะธะน ะฟะฐะบะตั
// ( ะฒ ัะปััะฐะต ะฒะพัััะฐะฝะพะฒะปะตะฝะธั ัะพะตะดะธะฝะตะฝะธั ัะทะตะป-ะฟัะธะตะผะฝะธะบ ะทะฐะฝะพะฒะพ ะพัะฟัะฐะฒะธั ะทะฐะฟัะพัั, ะบะพัะพััะต ะดะพ ะฝะตะณะพ ะฝะต ะดะพัะปะธ)
ReliableUdpStateTools.SendPacket(connectionRecord, ReliableUdpStateTools.RetransmissionCreateUdpPayload(connectionRecord, connectionRecord.SndNext - 1));
// ะฒะบะปััะฐะตะผ ัะฐะนะผะตั CloseWait โ ะดะปั ะพะถะธะดะฐะฝะธั ะฒะพัััะฐะฝะพะฒะปะตะฝะธั ัะพะตะดะธะฝะตะฝะธั ะธะปะธ ะตะณะพ ะทะฐะฒะตััะตะฝะธั
StartCloseWaitTimer(connectionRecord);
}
เชธเชเซเชทเชฎ เชชเซเชฐเซเชฃ เชชเชฆเซเชงเชคเชฟ เชเชพเชฒเซ เชฐเชนเซเชฒ เชเชพเชเชฎเชฐเชจเซ เชฌเชเชง เชเชฐเซ เชเซ เช
เชจเซ เชธเชฌเซเชธเซเชเซเชฐเชพเชเชฌเชฐเซเชธเชจเซ เชธเชเชฆเซเชถ เชฎเซเชเชฒเซ เชเซ.
เชชเซเชฐเซเชฃ.เชชเซเชฐเซเชธเซเชธ เชชเซเชเซเชเซเชธ:
public override void ProcessPackets(ReliableUdpConnectionRecord connectionRecord)
{
if (connectionRecord.WaitForPacketsTimer != null)
connectionRecord.WaitForPacketsTimer.Dispose();
// ัะพะฑะธัะฐะตะผ ัะพะพะฑัะตะฝะธะต ะธ ะฟะตัะตะดะฐะตะผ ะตะณะพ ะฟะพะดะฟะธััะธะบะฐะผ
ReliableUdpStateTools.CreateMessageFromMemoryStream(connectionRecord);
}
เชฐเซเชธเซเชตเชชเซเชเซเช เชชเชฆเซเชงเชคเชฟ
เชธเชเซเชทเชฎ เชซเชฐเซเชธเซเชเชชเซเชเซเช เชชเซเชฐเชพเชชเซเชค เชฅเชฏเซเช เชชเชฆเซเชงเชคเชฟเชจเซเช เชฎเซเชเซเชฏ เชเชพเชฐเซเชฏ เช เชจเชฟเชฐเซเชงเชพเชฐเชฟเชค เชเชฐเชตเชพเชจเซเช เชเซ เชเซ เชชเซเชฐเชฅเชฎ เชธเชเชฆเซเชถ เชชเซเชเซเช เชเชฐเซเชเชฐ เชเชจเซเชเชฐเชซเซเชธ เชชเชฐ เชเชตเซเชฏเซเช เชเซ เชเซ เชเซเชฎ, เช
เชจเซ เชเช เช เชชเซเชเซเชเชจเซ เชธเชฎเชพเชตเซเชถ เชเชฐเชคเซ เชธเชเชฆเซเชถ เชเชเชคเซเชฐเชฟเชค เชเชฐเชตเชพเชจเซ เชเซ.
FirstPacketReceived.ReceivePacket:
public override void ReceivePacket(ReliableUdpConnectionRecord connectionRecord, ReliableUdpHeader header, byte[] payload)
{
if (!header.Flags.HasFlag(ReliableUdpHeaderFlags.FirstPacket))
// ะพัะฑัะฐััะฒะฐะตะผ ะฟะฐะบะตั
return;
// ะบะพะผะฑะธะฝะฐัะธั ะดะฒัั
ัะปะฐะณะพะฒ - FirstPacket ะธ LastPacket - ะณะพะฒะพัะธั ััะพ ั ะฝะฐั ะตะดะธะฝััะฒะตะฝะฝะพะต ัะพะพะฑัะตะฝะธะต
if (header.Flags.HasFlag(ReliableUdpHeaderFlags.FirstPacket) &
header.Flags.HasFlag(ReliableUdpHeaderFlags.LastPacket))
{
ReliableUdpStateTools.CreateMessageFromSinglePacket(connectionRecord, header, payload.Slice(ReliableUdpHeader.Length, payload.Length));
if (!header.Flags.HasFlag(ReliableUdpHeaderFlags.NoAsk))
{
// ะพัะฟัะฐะฒะปัะตะผ ะฟะฐะบะตั ะฟะพะดัะฒะตัะถะดะตะฝะธะต
ReliableUdpStateTools.SendAcknowledgePacket(connectionRecord);
}
SetAsCompleted(connectionRecord);
return;
}
// by design ะฒัะต packet numbers ะฝะฐัะธะฝะฐัััั ั 0;
if (header.PacketNumber != 0)
return;
ReliableUdpStateTools.InitIncomingBytesStorage(connectionRecord, header);
ReliableUdpStateTools.WritePacketData(connectionRecord, header, payload);
// ััะธัะฐะตะผ ะบะพะป-ะฒะพ ะฟะฐะบะตัะพะฒ, ะบะพัะพััะต ะดะพะปะถะฝั ะฟัะธะนัะธ
connectionRecord.NumberOfPackets = (int)Math.Ceiling((double) ((double) connectionRecord.IncomingStream.Length/(double) connectionRecord.BufferSize));
// ะทะฐะฟะธััะฒะฐะตะผ ะฝะพะผะตั ะฟะพัะปะตะดะฝะตะณะพ ะฟะพะปััะตะฝะฝะพะณะพ ะฟะฐะบะตัะฐ (0)
connectionRecord.RcvCurrent = header.PacketNumber;
// ะฟะพัะปะต ัะดะฒะธะฝัะปะธ ะพะบะฝะพ ะฟัะธะตะผะฐ ะฝะฐ 1
connectionRecord.WindowLowerBound++;
// ะฟะตัะตะบะปััะฐะตะผ ัะพััะพัะฝะธะต
connectionRecord.State = connectionRecord.Tcb.States.Assembling;
// ะตัะปะธ ะฝะต ััะตะฑัะตััั ะผะตั
ะฐะฝะธะทะผ ะฟะพะดัะฒะตัะถะดะตะฝะธะต
// ะทะฐะฟััะบะฐะตะผ ัะฐะนะผะตั ะบะพัะพััะน ะฒััะฒะพะฑะพะดะธั ะฒัะต ััััะบัััั
if (header.Flags.HasFlag(ReliableUdpHeaderFlags.NoAsk))
{
connectionRecord.CloseWaitTimer = new Timer(DisposeByTimeout, connectionRecord, connectionRecord.ShortTimerPeriod, -1);
}
else
{
ReliableUdpStateTools.SendAcknowledgePacket(connectionRecord);
connectionRecord.WaitForPacketsTimer = new Timer(CheckByTimer, connectionRecord, connectionRecord.ShortTimerPeriod, -1);
}
}
เชธเชเซเชทเชฎ เชธเชพเชฏเชเชฒ เชฎเซเชเชฒเซ เชกเชฟเชฒเชฟเชตเชฐเซ เชธเซเชตเซเชเซเชคเชฟเช เช
เชจเซ เชชเซเชจเชเชชเซเชฐเชธเชพเชฐเชฃ เชตเชฟเชจเชเชคเซเช เชธเซเชตเซเชเชพเชฐเชตเชพ เชฎเชพเชเซ เช เชชเชฆเซเชงเชคเชฟเชจเซ เชเชตเชฐเชฐเชพเชเชก เชเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ.
SendingCycle.ReceivePacket:
public override void ReceivePacket(ReliableUdpConnectionRecord connectionRecord, ReliableUdpHeader header, byte[] payload)
{
if (connectionRecord.IsDone != 0)
return;
if (!header.Flags.HasFlag(ReliableUdpHeaderFlags.RequestForPacket))
return;
// ัะฐััะตั ะบะพะฝะตัะฝะพะน ะณัะฐะฝะธัั ะพะบะฝะฐ
// ะฑะตัะตััั ะณัะฐะฝะธัะฐ ะพะบะฝะฐ + 1, ะดะปั ะฟะพะปััะตะฝะธั ะฟะพะดัะฒะตัะถะดะตะฝะธะน ะดะพััะฐะฒะบะธ
int windowHighestBound = Math.Min((connectionRecord.WindowLowerBound + connectionRecord.WindowSize), (connectionRecord.NumberOfPackets));
// ะฟัะพะฒะตัะบะฐ ะฝะฐ ะฟะพะฟะฐะดะฐะฝะธะต ะฒ ะพะบะฝะพ
if (header.PacketNumber < connectionRecord.WindowLowerBound || header.PacketNumber > windowHighestBound)
return;
connectionRecord.WaitForPacketsTimer.Change(connectionRecord.ShortTimerPeriod, -1);
if (connectionRecord.CloseWaitTimer != null)
connectionRecord.CloseWaitTimer.Change(-1, -1);
// ะฟัะพะฒะตัะธัั ะฝะฐ ะฟะพัะปะตะดะฝะธะน ะฟะฐะบะตั:
if (header.PacketNumber == connectionRecord.NumberOfPackets)
{
// ะฟะตัะตะดะฐัะฐ ะทะฐะฒะตััะตะฝะฐ
Interlocked.Increment(ref connectionRecord.IsDone);
SetAsCompleted(connectionRecord);
return;
}
// ััะพ ะพัะฒะตั ะฝะฐ ะฟะตัะฒัะน ะฟะฐะบะตั c ะฟะพะดัะฒะตัะถะดะตะฝะธะตะผ
if ((header.Flags.HasFlag(ReliableUdpHeaderFlags.FirstPacket) && header.PacketNumber == 1))
{
// ะฑะตะท ัะดะฒะธะณะฐ ะพะบะฝะฐ
SendPacket(connectionRecord);
}
// ะฟัะธัะปะพ ะฟะพะดัะฒะตัะถะดะตะฝะธะต ะพ ะฟะพะปััะตะฝะธะธ ะฑะปะพะบะฐ ะดะฐะฝะฝัั
else if (header.PacketNumber == windowHighestBound)
{
// ัะดะฒะธะณะฐะตะผ ะพะบะฝะพ ะฟัะธะตะผ/ะฟะตัะตะดะฐัะธ
connectionRecord.WindowLowerBound += connectionRecord.WindowSize;
// ะพะฑะฝัะปัะตะผ ะผะฐััะธะฒ ะบะพะฝััะพะปั ะฟะตัะตะดะฐัะธ
connectionRecord.WindowControlArray.Nullify();
// ะพัะฟัะฐะฒะปัะตะผ ะฑะปะพะบ ะฟะฐะบะตัะพะฒ
SendPacket(connectionRecord);
}
// ััะพ ะทะฐะฟัะพั ะฝะฐ ะฟะพะฒัะพัะฝัั ะฟะตัะตะดะฐัั โ ะพัะฟัะฐะฒะปัะตะผ ััะตะฑัะตะผัะน ะฟะฐะบะตั
else
ReliableUdpStateTools.SendPacket(connectionRecord, ReliableUdpStateTools.RetransmissionCreateUdpPayload(connectionRecord, header.PacketNumber));
}
เชธเชเซเชทเชฎ เชเชธเซเชฎเซเชฌเชฒเชฟเชเช ReceivePacket เชชเชฆเซเชงเชคเชฟเชฎเชพเช, เชเชตเชจเชพเชฐเชพ เชชเซเชเซเชเซเชฎเชพเชเชฅเซ เชธเชเชฆเซเชถเชจเซ เชเชธเซเชฎเซเชฌเชฒ เชเชฐเชตเชพเชจเซเช เชฎเซเชเซเชฏ เชเชพเชฐเซเชฏ เชฅเชพเชฏ เชเซ.
เชเชธเซเชฎเซเชฌเชฒเซเชเช.เชฐเชฟเชธเซเชตเชชเซเชเซเช:
public override void ReceivePacket(ReliableUdpConnectionRecord connectionRecord, ReliableUdpHeader header, byte[] payload)
{
if (connectionRecord.IsDone != 0)
return;
// ะพะฑัะฐะฑะพัะบะฐ ะฟะฐะบะตัะพะฒ ั ะพัะบะปััะตะฝะฝัะผ ะผะตั
ะฐะฝะธะทะผะพะผ ะฟะพะดัะฒะตัะถะดะตะฝะธั ะดะพััะฐะฒะบะธ
if (header.Flags.HasFlag(ReliableUdpHeaderFlags.NoAsk))
{
// ัะฑัะฐััะฒะฐะตะผ ัะฐะนะผะตั
connectionRecord.CloseWaitTimer.Change(connectionRecord.LongTimerPeriod, -1);
// ะทะฐะฟะธััะฒะฐะตะผ ะดะฐะฝะฝัะต
ReliableUdpStateTools.WritePacketData(connectionRecord, header, payload);
// ะตัะปะธ ะฟะพะปััะธะปะธ ะฟะฐะบะตั ั ะฟะพัะปะตะดะฝะธะผ ัะปะฐะณะพะผ - ะดะตะปะฐะตะผ ะทะฐะฒะตััะฐะตะผ
if (header.Flags.HasFlag(ReliableUdpHeaderFlags.LastPacket))
{
connectionRecord.State = connectionRecord.Tcb.States.Completed;
connectionRecord.State.ProcessPackets(connectionRecord);
}
return;
}
// ัะฐััะตั ะบะพะฝะตัะฝะพะน ะณัะฐะฝะธัั ะพะบะฝะฐ
int windowHighestBound = Math.Min((connectionRecord.WindowLowerBound + connectionRecord.WindowSize - 1), (connectionRecord.NumberOfPackets - 1));
// ะพัะฑัะฐััะฒะฐะตะผ ะฝะต ะฟะพะฟะฐะดะฐััะธะต ะฒ ะพะบะฝะพ ะฟะฐะบะตัั
if (header.PacketNumber < connectionRecord.WindowLowerBound || header.PacketNumber > (windowHighestBound))
return;
// ะพัะฑัะฐััะฒะฐะตะผ ะดัะฑะปะธะบะฐัั
if (connectionRecord.WindowControlArray.Contains(header.PacketNumber))
return;
// ะทะฐะฟะธััะฒะฐะตะผ ะดะฐะฝะฝัะต
ReliableUdpStateTools.WritePacketData(connectionRecord, header, payload);
// ัะฒะตะปะธัะธะฒะฐะตะผ ััะตััะธะบ ะฟะฐะบะตัะพะฒ
connectionRecord.PacketCounter++;
// ะทะฐะฟะธััะฒะฐะตะผ ะฒ ะผะฐััะธะฒ ัะฟัะฐะฒะปะตะฝะธั ะพะบะฝะพะผ ัะตะบััะธะน ะฝะพะผะตั ะฟะฐะบะตัะฐ
connectionRecord.WindowControlArray[header.PacketNumber - connectionRecord.WindowLowerBound] = header.PacketNumber;
// ัััะฐะฝะฐะฒะปะธะฒะฐะตะผ ะฝะฐะธะฑะพะปััะธะน ะฟัะธัะตะดัะธะน ะฟะฐะบะตั
if (header.PacketNumber > connectionRecord.RcvCurrent)
connectionRecord.RcvCurrent = header.PacketNumber;
// ะฟะตัะตะทะฐะฟััะบะฐะผ ัะฐะนะผะตัั
connectionRecord.TimerSecondTry = false;
connectionRecord.WaitForPacketsTimer.Change(connectionRecord.ShortTimerPeriod, -1);
if (connectionRecord.CloseWaitTimer != null)
connectionRecord.CloseWaitTimer.Change(-1, -1);
// ะตัะปะธ ะฟัะธัะตะป ะฟะพัะปะตะดะฝะธะน ะฟะฐะบะตั
if (header.Flags.HasFlag(ReliableUdpHeaderFlags.LastPacket))
{
Interlocked.Increment(ref connectionRecord.IsLastPacketReceived);
}
// ะตัะปะธ ะฝะฐะผ ะฟัะธัะปะธ ะฒัะต ะฟะฐะบะตัั ะพะบะฝะฐ, ัะพ ัะฑัะฐััะฒะฐะตะผ ััะตััะธะบ
// ะธ ะฒัััะปะฐะตะผ ะฟะฐะบะตั ะฟะพะดัะฒะตัะถะดะตะฝะธะต
else if (connectionRecord.PacketCounter == connectionRecord.WindowSize)
{
// ัะฑัะฐััะฒะฐะตะผ ััะตััะธะบ.
connectionRecord.PacketCounter = 0;
// ัะดะฒะธะฝัะปะธ ะพะบะฝะพ ะฟะตัะตะดะฐัะธ
connectionRecord.WindowLowerBound += connectionRecord.WindowSize;
// ะพะฑะฝัะปะตะฝะธะต ะผะฐััะธะฒะฐ ัะฟัะฐะฒะปะตะฝะธั ะฟะตัะตะดะฐัะตะน
connectionRecord.WindowControlArray.Nullify();
ReliableUdpStateTools.SendAcknowledgePacket(connectionRecord);
}
// ะตัะปะธ ะฟะพัะปะตะดะฝะธะน ะฟะฐะบะตั ัะถะต ะธะผะตะตััั
if (Thread.VolatileRead(ref connectionRecord.IsLastPacketReceived) != 0)
{
// ะฟัะพะฒะตััะตะผ ะฟะฐะบะตัั
ProcessPackets(connectionRecord);
}
}
เชธเชเซเชทเชฎ เชชเซเชฐเซเชฃ เชชเชฆเซเชงเชคเชฟเชจเซเช เชเชเชฎเชพเชคเซเชฐ เชเชพเชฐเซเชฏ เชธเชเชฆเซเชถเชจเชพ เชธเชซเชณ เชตเชฟเชคเชฐเชฃเชจเซ เชชเซเชจเช เชธเซเชตเซเชเซเชคเชฟ เชฎเซเชเชฒเชตเชพเชจเซเช เชเซ.
เชชเซเชฐเซเชฃ เชฅเชฏเซเช.เชชเซเชเซเช เชชเซเชฐเชพเชชเซเชค เชเชฐเซ:
public override void ReceivePacket(ReliableUdpConnectionRecord connectionRecord, ReliableUdpHeader header, byte[] payload)
{
// ะฟะพะฒัะพัะฝะฐั ะพัะฟัะฐะฒะบะฐ ะฟะพัะปะตะดะฝะตะณะพ ะฟะฐะบะตัะฐ ะฒ ัะฒัะทะธ ั ัะตะผ,
// ััะพ ะฟะพัะปะตะดะฝะธะน ack ะฝะต ะดะพัะตะป ะดะพ ะพัะฟัะฐะฒะธัะตะปั
if (header.Flags.HasFlag(ReliableUdpHeaderFlags.LastPacket))
{
ReliableUdpStateTools.SendAcknowledgePacket(connectionRecord);
}
}
เชชเซเชเซเช เชชเชฆเซเชงเชคเชฟ เชฎเซเชเชฒเซ
เชธเชเซเชทเชฎ FirstPacketSending เช เชชเชฆเซเชงเชคเชฟ เชกเซเชเชพเชจเซเช เชชเซเชฐเชฅเชฎ เชชเซเชเซเช เชฎเซเชเชฒเซ เชเซ, เช
เชฅเชตเชพ เชเซ เชธเชเชฆเซเชถเชจเซ เชกเชฟเชฒเชฟเชตเชฐเซ เชชเซเชทเซเชเชฟเชจเซ เชเชฐเซเชฐ เชจเชฅเซ, เชคเซ เชธเชฎเชเซเชฐ เชธเชเชฆเซเชถ.
FirstPacketSending.SendPacket:
public override void SendPacket(ReliableUdpConnectionRecord connectionRecord)
{
connectionRecord.PacketCounter = 0;
connectionRecord.SndNext = 0;
connectionRecord.WindowLowerBound = 0;
// ะตัะปะธ ะฟะพะดัะฒะตัะถะดะตะฝะธั ะฝะต ััะตะฑัะตััั - ะพัะฟัะฐะฒะปัะตะผ ะฒัะต ะฟะฐะบะตัั
// ะธ ะฒััะฒะพะฑะพะถะดะฐะตะผ ัะตััััั
if (connectionRecord.IsNoAnswerNeeded)
{
// ะะดะตัั ะฟัะพะธัั
ะพะดะธั ะพัะฟัะฐะฒะบะฐ As Is
do
{
ReliableUdpStateTools.SendPacket(connectionRecord, ReliableUdpStateTools.CreateUdpPayload(connectionRecord, ReliableUdpStateTools. CreateReliableUdpHeader(connectionRecord)));
connectionRecord.SndNext++;
} while (connectionRecord.SndNext < connectionRecord.NumberOfPackets);
SetAsCompleted(connectionRecord);
return;
}
// ัะพะทะดะฐะตะผ ะทะฐะณะพะปะพะฒะพะบ ะฟะฐะบะตัะฐ ะธ ะพัะฟัะฐะฒะปัะตะผ ะตะณะพ
ReliableUdpHeader header = ReliableUdpStateTools.CreateReliableUdpHeader(connectionRecord);
ReliableUdpStateTools.SendPacket(connectionRecord, ReliableUdpStateTools.CreateUdpPayload(connectionRecord, header));
// ัะฒะตะปะธัะธะฒะฐะตะผ ััะตััะธะบ
connectionRecord.SndNext++;
// ัะดะฒะธะณะฐะตะผ ะพะบะฝะพ
connectionRecord.WindowLowerBound++;
connectionRecord.State = connectionRecord.Tcb.States.SendingCycle;
// ะะฐะฟััะบะฐะตะผ ัะฐะนะผะตั
connectionRecord.WaitForPacketsTimer = new Timer(CheckByTimer, connectionRecord, connectionRecord.ShortTimerPeriod, -1);
}
เชธเชเซเชทเชฎ เชธเชพเชฏเชเชฒ เชฎเซเชเชฒเซ เช เชชเชฆเซเชงเชคเชฟเชฎเชพเช, เชชเซเชเซเชเซเชจเซ เชฌเซเชฒเซเช เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซ เชเซ.
SendingCycle.SendPacket:
public override void SendPacket(ReliableUdpConnectionRecord connectionRecord)
{
// ะพัะฟัะฐะฒะปัะตะผ ะฑะปะพะบ ะฟะฐะบะตัะพะฒ
for (connectionRecord.PacketCounter = 0;
connectionRecord.PacketCounter < connectionRecord.WindowSize &&
connectionRecord.SndNext < connectionRecord.NumberOfPackets;
connectionRecord.PacketCounter++)
{
ReliableUdpHeader header = ReliableUdpStateTools.CreateReliableUdpHeader(connectionRecord);
ReliableUdpStateTools.SendPacket(connectionRecord, ReliableUdpStateTools.CreateUdpPayload(connectionRecord, header));
connectionRecord.SndNext++;
}
// ะฝะฐ ัะปััะฐะน ะฑะพะปััะพะณะพ ะพะบะฝะฐ ะฟะตัะตะดะฐัะธ, ะฟะตัะตะทะฐะฟััะบะฐะตะผ ัะฐะนะผะตั ะฟะพัะปะต ะพัะฟัะฐะฒะบะธ
connectionRecord.WaitForPacketsTimer.Change( connectionRecord.ShortTimerPeriod, -1 );
if ( connectionRecord.CloseWaitTimer != null )
{
connectionRecord.CloseWaitTimer.Change( -1, -1 );
}
}
เชเซเชกเชฎเชพเช เชตเชงเซ เชเชเชกเซ. เชเซเชกเชพเชฃเซ เชฌเชจเชพเชตเชตเชพ เช
เชจเซ เชธเซเชฅเชพเชชเชฟเชค เชเชฐเชตเชพ
เชนเชตเซ เชเซเชฏเชพเชฐเซ เชเชชเชฃเซ เชฎเซเชณเชญเซเชค เชธเซเชฅเชฟเชคเชฟเช เช
เชจเซ เชฐเชพเชเซเชฏเซเชจเซ เชนเซเชจเซเชกเชฒ เชเชฐเชตเชพ เชฎเชพเชเซ เชเชชเชฏเซเชเชฎเชพเช เชฒเซเชตเชพเชคเซ เชชเชฆเซเชงเชคเชฟเช เชเซเช เชเซ, เชเชพเชฒเซ เชชเซเชฐเซเชเซเชเซเชฒ เชเซเชตเซ เชฐเซเชคเซ เชเชพเชฐเซเชฏ เชเชฐเซ เชเซ เชคเซเชจเชพ เชฅเซเชกเชพ เชเชฆเชพเชนเชฐเชฃเซเชจเซ เชฅเซเชกเซ เชตเชงเซ เชตเชฟเชเชคเชฎเชพเช เชคเซเชกเซเช.
เชธเชพเชฎเชพเชจเซเชฏ เชธเซเชฅเชฟเชคเชฟเชฎเชพเช เชกเซเชเชพ เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชกเชพเชฏเชพเชเซเชฐเชพเชฎ:
เชฐเชเชจเชพเชจเซ เชตเชฟเชเชคเชตเชพเชฐ เชงเซเชฏเชพเชจเชฎเชพเช เชฒเซ เชเชจเซเชเซเชถเชจ เชฐเซเชเซเชฐเซเชก เชเชจเซเชเซเช เชเชฐเชตเชพ เช
เชจเซ เชชเซเชฐเชฅเชฎ เชชเซเชเซเช เชฎเซเชเชฒเชตเชพ เชฎเชพเชเซ. เชเซเชฐเชพเชจเซเชธเชซเชฐ เชนเชเชฎเซเชถเชพ เชเชชเซเชฒเซเชเซเชถเชจ เชฆเซเชตเชพเชฐเชพ เชถเชฐเซ เชเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ เชเซ เชธเซเชจเซเชก เชฎเซเชธเซเช API เชจเซ เชเซเชฒ เชเชฐเซ เชเซ. เชเชเชณ, เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชเชเชเซเชฐเซเชฒ เชฌเซเชฒเซเชเชจเซ เชธเซเชเชพเชฐเซเช เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชชเชฆเซเชงเชคเชฟเชจเซ เชเชชเชฏเซเช เชเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ, เชเซ เชจเชตเชพ เชธเชเชฆเซเชถ เชฎเชพเชเซ เชกเซเชเชพเชจเซเช เชชเซเชฐเชธเชพเชฐเชฃ เชถเชฐเซ เชเชฐเซ เชเซ.
เชเชเชเชเซเชเชเช เชเชจเซเชเซเชถเชจ เชฌเชจเชพเชตเชตเซเช:
private void StartTransmission(ReliableUdpMessage reliableUdpMessage, EndPoint endPoint, AsyncResultSendMessage asyncResult)
{
if (m_isListenerStarted == 0)
{
if (this.LocalEndpoint == null)
{
throw new ArgumentNullException( "", "You must use constructor with parameters or start listener before sending message" );
}
// ะทะฐะฟััะบะฐะตะผ ะพะฑัะฐะฑะพัะบั ะฒั
ะพะดััะธั
ะฟะฐะบะตัะพะฒ
StartListener(LocalEndpoint);
}
// ัะพะทะดะฐะตะผ ะบะปัั ะดะปั ัะปะพะฒะฐัั, ะฝะฐ ะพัะฝะพะฒะต EndPoint ะธ ReliableUdpHeader.TransmissionId
byte[] transmissionId = new byte[4];
// ัะพะทะดะฐะตะผ ัะปััะฐะนะฝัะน ะฝะพะผะตั transmissionId
m_randomCrypto.GetBytes(transmissionId);
Tuple<EndPoint, Int32> key = new Tuple<EndPoint, Int32>(endPoint, BitConverter.ToInt32(transmissionId, 0));
// ัะพะทะดะฐะตะผ ะฝะพะฒัั ะทะฐะฟะธัั ะดะปั ัะพะตะดะธะฝะตะฝะธั ะธ ะฟัะพะฒะตััะตะผ,
// ัััะตััะฒัะตั ะปะธ ัะถะต ัะฐะบะพะน ะฝะพะผะตั ะฒ ะฝะฐัะธั
ัะปะพะฒะฐััั
if (!m_listOfHandlers.TryAdd(key, new ReliableUdpConnectionRecord(key, this, reliableUdpMessage, asyncResult)))
{
// ะตัะปะธ ัััะตััะฒัะตั โ ัะพ ะฟะพะฒัะพัะฝะพ ะณะตะฝะตัะธััะตะผ ัะปััะฐะนะฝัะน ะฝะพะผะตั
m_randomCrypto.GetBytes(transmissionId);
key = new Tuple<EndPoint, Int32>(endPoint, BitConverter.ToInt32(transmissionId, 0));
if (!m_listOfHandlers.TryAdd(key, new ReliableUdpConnectionRecord(key, this, reliableUdpMessage, asyncResult)))
// ะตัะปะธ ัะฝะพะฒะฐ ะฝะต ัะดะฐะปะพัั โ ะณะตะฝะตัะธััะตะผ ะธัะบะปััะตะฝะธะต
throw new ArgumentException("Pair TransmissionId & EndPoint is already exists in the dictionary");
}
// ะทะฐะฟัััะธะปะธ ัะพััะพัะฝะธะต ะฒ ะพะฑัะฐะฑะพัะบั
m_listOfHandlers[key].State.SendPacket(m_listOfHandlers[key]);
}
เชชเชนเซเชฒเซเช เชชเซเชเซเช เชฎเซเชเชฒเซ เชฐเชนเซเชฏเซเช เชเซ (FirstPacketSending State):
public override void SendPacket(ReliableUdpConnectionRecord connectionRecord)
{
connectionRecord.PacketCounter = 0;
connectionRecord.SndNext = 0;
connectionRecord.WindowLowerBound = 0;
// ...
// ัะพะทะดะฐะตะผ ะทะฐะณะพะปะพะฒะพะบ ะฟะฐะบะตัะฐ ะธ ะพัะฟัะฐะฒะปัะตะผ ะตะณะพ
ReliableUdpHeader header = ReliableUdpStateTools.CreateReliableUdpHeader(connectionRecord);
ReliableUdpStateTools.SendPacket(connectionRecord, ReliableUdpStateTools.CreateUdpPayload(connectionRecord, header));
// ัะฒะตะปะธัะธะฒะฐะตะผ ััะตััะธะบ
connectionRecord.SndNext++;
// ัะดะฒะธะณะฐะตะผ ะพะบะฝะพ
connectionRecord.WindowLowerBound++;
// ะฟะตัะตั
ะพะดะธะผ ะฒ ัะพััะพัะฝะธะต SendingCycle
connectionRecord.State = connectionRecord.Tcb.States.SendingCycle;
// ะะฐะฟััะบะฐะตะผ ัะฐะนะผะตั
connectionRecord.WaitForPacketsTimer = new Timer(CheckByTimer, connectionRecord, connectionRecord.ShortTimerPeriod, -1);
}
เชชเซเชฐเชฅเชฎ เชชเซเชเซเช เชฎเซเชเชฒเซเชฏเชพ เชชเชเซ, เชฎเซเชเชฒเชจเชพเชฐ เชฐเชพเชเซเชฏเชฎเชพเช เชชเซเชฐเชตเซเชถ เชเชฐเซ เชเซ เชธเชพเชฏเชเชฒ เชฎเซเชเชฒเซ - เชชเซเชเซเช เชตเชฟเชคเชฐเชฃเชจเซ เชชเซเชทเซเชเชฟ เชฎเชพเชเซ เชฐเชพเชน เชเซเช.
เชชเซเชฐเชพเชชเซเชค เชเชฐเชจเชพเชฐ เชฌเชพเชเซ, EndReceive เชชเชฆเซเชงเชคเชฟเชจเซ เชเชชเชฏเซเช เชเชฐเซเชจเซ, เชฎเซเชเชฒเซเชฒ เชชเซเชเซเช เชฎเซเชณเชตเซ เชเซ, เชเช เชจเชตเซเช เชฌเชจเชพเชตเซ เชเซ เชเชจเซเชเซเชถเชจ เชฐเซเชเซเชฐเซเชก เช
เชจเซ เช เชชเซเชเซเชเชจเซ, เชชเซเชฐเซ-เชชเชพเชฐเซเชธ เชนเซเชกเชฐ เชธเชพเชฅเซ, เชชเซเชฐเชเซเชฐเชฟเชฏเชพ เชฎเชพเชเซ เชฐเชพเชเซเชฏเชจเซ เชฐเซเชธเซเชตเชชเซเชเซเช เชชเชฆเซเชงเชคเชฟเชฎเชพเช เชชเชธเชพเชฐ เชเชฐเซ เชเซ. เชซเชฐเซเชธเซเชเชชเซเชเซเช เชชเซเชฐเชพเชชเซเชค เชฅเชฏเซเช
เชชเซเชฐเชพเชชเซเชคเชฟ เชฌเชพเชเซ เชชเชฐ เชเชจเซเชเซเชถเชจ เชฌเชจเชพเชตเชตเซเช:
private void EndReceive(IAsyncResult ar)
{
// ...
// ะฟะฐะบะตั ะฟะพะปััะตะฝ
// ะฟะฐััะธะผ ะทะฐะณะพะปะพะฒะพะบ ะฟะฐะบะตัะฐ
ReliableUdpHeader header;
if (!ReliableUdpStateTools.ReadReliableUdpHeader(bytes, out header))
{
// ะฟัะธัะตะป ะฝะตะบะพััะตะบัะฝัะน ะฟะฐะบะตั - ะพัะฑัะฐััะฒะฐะตะผ ะตะณะพ
return;
}
// ะบะพะฝััััะธััะตะผ ะบะปัั ะดะปั ะพะฟัะตะดะตะปะตะฝะธั connection recordโะฐ ะดะปั ะฟะฐะบะตัะฐ
Tuple<EndPoint, Int32> key = new Tuple<EndPoint, Int32>(connectedClient, header.TransmissionId);
// ะฟะพะปััะฐะตะผ ัััะตััะฒััััั connection record ะธะปะธ ัะพะทะดะฐะตะผ ะฝะพะฒัั
ReliableUdpConnectionRecord record = m_listOfHandlers.GetOrAdd(key, new ReliableUdpConnectionRecord(key, this, header. ReliableUdpMessageType));
// ะทะฐะฟััะบะฐะตะผ ะฟะฐะบะตั ะฒ ะพะฑัะฐะฑะพัะบั ะฒ ะบะพะฝะตัะฝัะน ะฐะฒัะพะผะฐั
record.State.ReceivePacket(record, header, bytes);
}
เชชเซเชฐเชฅเชฎ เชชเซเชเซเช เชชเซเชฐเชพเชชเซเชค เชเชฐเชตเซเช เช เชจเซ เชธเซเชตเซเชเซเชคเชฟ เชฎเซเชเชฒเชตเซ (เชซเชฐเซเชธเซเชเชชเซเชเซเช เชชเซเชฐเชพเชชเซเชค เชฐเชพเชเซเชฏ):
public override void ReceivePacket(ReliableUdpConnectionRecord connectionRecord, ReliableUdpHeader header, byte[] payload)
{
if (!header.Flags.HasFlag(ReliableUdpHeaderFlags.FirstPacket))
// ะพัะฑัะฐััะฒะฐะตะผ ะฟะฐะบะตั
return;
// ...
// by design ะฒัะต packet numbers ะฝะฐัะธะฝะฐัััั ั 0;
if (header.PacketNumber != 0)
return;
// ะธะฝะธัะธะฐะปะธะทะธััะตะผ ะผะฐััะธะฒ ะดะปั ั
ัะฐะฝะตะฝะธั ัะฐััะตะน ัะพะพะฑัะตะฝะธั
ReliableUdpStateTools.InitIncomingBytesStorage(connectionRecord, header);
// ะทะฐะฟะธััะฒะฐะตะผ ะดะฐะฝะฝัะต ะฟะฐะบะตั ะฒ ะผะฐััะธะฒ
ReliableUdpStateTools.WritePacketData(connectionRecord, header, payload);
// ััะธัะฐะตะผ ะบะพะป-ะฒะพ ะฟะฐะบะตัะพะฒ, ะบะพัะพััะต ะดะพะปะถะฝั ะฟัะธะนัะธ
connectionRecord.NumberOfPackets = (int)Math.Ceiling((double) ((double) connectionRecord.IncomingStream.Length/(double) connectionRecord.BufferSize));
// ะทะฐะฟะธััะฒะฐะตะผ ะฝะพะผะตั ะฟะพัะปะตะดะฝะตะณะพ ะฟะพะปััะตะฝะฝะพะณะพ ะฟะฐะบะตัะฐ (0)
connectionRecord.RcvCurrent = header.PacketNumber;
// ะฟะพัะปะต ัะดะฒะธะฝัะปะธ ะพะบะฝะพ ะฟัะธะตะผะฐ ะฝะฐ 1
connectionRecord.WindowLowerBound++;
// ะฟะตัะตะบะปััะฐะตะผ ัะพััะพัะฝะธะต
connectionRecord.State = connectionRecord.Tcb.States.Assembling;
if (/*ะตัะปะธ ะฝะต ััะตะฑัะตััั ะผะตั
ะฐะฝะธะทะผ ะฟะพะดัะฒะตัะถะดะตะฝะธะต*/)
// ...
else
{
// ะพัะฟัะฐะฒะปัะตะผ ะฟะพะดัะฒะตัะถะดะตะฝะธะต
ReliableUdpStateTools.SendAcknowledgePacket(connectionRecord);
connectionRecord.WaitForPacketsTimer = new Timer(CheckByTimer, connectionRecord, connectionRecord.ShortTimerPeriod, -1);
}
}
เชเซเชกเชฎเชพเช เชตเชงเซ เชเชเชกเซ. เชธเชฎเชฏเชธเชฎเชพเชชเซเชคเชฟ เชชเชฐ เชเชจเซเชเซเชถเชจ เชฌเชเชง เชเชฐเซ เชฐเชนเซเชฏเซเช เชเซ
เชเชพเชเชฎเชเชเช เชนเซเชจเซเชกเชฒเชฟเชเช เช เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP เชจเซ เชฎเชนเชคเซเชตเชชเซเชฐเซเชฃ เชญเชพเช เชเซ. เชเช เชเชฆเชพเชนเชฐเชฃเชจเซ เชตเชฟเชเชพเชฐ เชเชฐเซ เชเซเชฎเชพเช เชฎเชงเซเชฏเชตเชฐเซเชคเซ เชจเซเชก เชจเชฟเชทเซเชซเชณ เชเชฏเซ เช
เชจเซ เชฌเชเชจเซ เชฆเชฟเชถเชพเชฎเชพเช เชกเซเชเชพ เชกเชฟเชฒเชฟเชตเชฐเซ เช
เชถเชเซเชฏ เชฌเชจเซ เชเช.
เชธเชฎเชฏเชธเชฎเชพเชชเซเชคเชฟ เชฆเซเชตเชพเชฐเชพ เชเชจเซเชเซเชถเชจ เชฌเชเชง เชเชฐเชตเชพ เชฎเชพเชเซเชจเซ เชเชเซเชคเชฟ:
เชกเชพเชฏเชพเชเซเชฐเชพเชฎเชฎเชพเชเชฅเซ เชเซเช เชถเชเชพเชฏ เชเซ เชคเซเชฎ, เชชเซเชเซเชเชจเชพ เชฌเซเชฒเซเช เชฎเซเชเชฒเซเชฏเชพ เชชเชเซ เชคเชฐเชค เช เชฎเซเชเชฒเชจเชพเชฐเชจเซเช เชเชพเชฐเซเชฏ เชเชพเชเชฎเชฐ เชถเชฐเซ เชฅเชพเชฏ เชเซ. เช เชฐเชพเชเซเชฏเชจเซ SendPacket เชชเชฆเซเชงเชคเชฟเชฎเชพเช เชฅเชพเชฏ เชเซ เชธเชพเชฏเชเชฒ เชฎเซเชเชฒเซ.
เชตเชฐเซเช เชเชพเชเชฎเชฐเชจเซ เชธเชเซเชทเชฎ เชเชฐเชตเซเช (เชธเซเชจเซเชกเชฟเชเชเชธเชพเชฏเชเชฒ เชธเซเชเซเช):
public override void SendPacket(ReliableUdpConnectionRecord connectionRecord)
{
// ะพัะฟัะฐะฒะปัะตะผ ะฑะปะพะบ ะฟะฐะบะตัะพะฒ
// ...
// ะฟะตัะตะทะฐะฟััะบะฐะตะผ ัะฐะนะผะตั ะฟะพัะปะต ะพัะฟัะฐะฒะบะธ
connectionRecord.WaitForPacketsTimer.Change( connectionRecord.ShortTimerPeriod, -1 );
if ( connectionRecord.CloseWaitTimer != null )
connectionRecord.CloseWaitTimer.Change( -1, -1 );
}
เชเซเชฏเชพเชฐเซ เชเชจเซเชเซเชถเชจ เชฌเชจเชพเชตเชตเชพเชฎเชพเช เชเชตเซ เชคเซเชฏเชพเชฐเซ เชเชพเชเชฎเชฐ เชชเซเชฐเชฟเชฏเชกเซเชธ เชธเซเช เชเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ. เชกเชฟเชซเซเชฒเซเช ShortTimerPeriod 5 เชธเซเชเชจเซเชก เชเซ. เชเชฆเชพเชนเชฐเชฃเชฎเชพเช, เชคเซ 1,5 เชธเซเชเชจเซเชก เชชเชฐ เชธเซเช เชเซ.
เชเชจเชเชฎเชฟเชเช เชเชจเซเชเซเชถเชจ เชฎเชพเชเซ, เชเชพเชเชฎเชฐ เชเซเชฒเซเชฒเซเช เชเชจเชเชฎเชฟเชเช เชกเซเชเชพ เชชเซเชเซเช เชชเซเชฐเชพเชชเซเชค เชเชฐเซเชฏเชพ เชชเชเซ เชถเชฐเซ เชฅเชพเชฏ เชเซ, เช เชฐเชพเชเซเชฏเชจเซ เชฐเซเชธเซเชตเชชเซเชเซเช เชชเชฆเซเชงเชคเชฟเชฎเชพเช เชฅเชพเชฏ เชเซ เชเชธเซเชฎเซเชฌเชฒเชฟเชเช
เชตเชฐเซเช เชเชพเชเชฎเชฐเชจเซ เชธเชเซเชทเชฎ เชเชฐเชตเซเช (เชเชธเซเชฎเซเชฌเชฒเชฟเชเช เชธเซเชเซเช):
public override void ReceivePacket(ReliableUdpConnectionRecord connectionRecord, ReliableUdpHeader header, byte[] payload)
{
// ...
// ะฟะตัะตะทะฐะฟััะบะฐะตะผ ัะฐะนะผะตัั
connectionRecord.TimerSecondTry = false;
connectionRecord.WaitForPacketsTimer.Change(connectionRecord.ShortTimerPeriod, -1);
if (connectionRecord.CloseWaitTimer != null)
connectionRecord.CloseWaitTimer.Change(-1, -1);
// ...
}
เชเชพเชฐเซเชฏเชเชพเชฐเซ เชเชพเชเชฎเชฐเชจเซ เชฐเชพเชน เชเซเชคเซ เชตเชเชคเซ เชเชจเชเชฎเชฟเชเช เชเชจเซเชเซเชถเชจ เชชเชฐ เชเซเช เชตเชงเซ เชชเซเชเซเช เชเชตเซเชฏเชพ เชจเชฅเซ. เชเชพเชเชฎเชฐ เชฌเชเชง เชฅเช เชเชฏเซเช เช
เชจเซ เชชเซเชฐเซเชธเซเชธเชชเซเชเซเชเซเชธ เชชเชฆเซเชงเชคเชฟเชจเซ เชฌเซเชฒเชพเชตเชตเชพเชฎเชพเช เชเชตเซ, เชเซเชฏเชพเช เชเซเชตเชพเชฏเซเชฒเชพ เชชเซเชเซเชเซ เชฎเชณเซเชฏเชพ เช
เชจเซ เชซเชฐเซเชฅเซ เชกเชฟเชฒเชฟเชตเชฐเซ เชตเชฟเชจเชเชคเซเช เชชเซเชฐเชฅเชฎ เชตเชเชค เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซ.
เชชเซเชจเช เชตเชฟเชคเชฐเชฃ เชตเชฟเชจเชเชคเซเช เชฎเซเชเชฒเซ เชฐเชนเซเชฏเซเช เชเซ (เชเชธเซเชฎเซเชฌเชฒเชฟเชเช เชธเซเชเซเช):
public override void ProcessPackets(ReliableUdpConnectionRecord connectionRecord)
{
// ...
if (/*ะฟัะพะฒะตัะบะฐ ะฝะฐ ะฟะพัะตััะฝะฝัะต ะฟะฐะบะตัั */)
{
// ะพัะฟัะฐะฒะปัะตะผ ะทะฐะฟัะพัั ะฝะฐ ะฟะพะฒัะพัะฝัั ะดะพััะฐะฒะบั
// ัััะฐะฝะฐะฒะปะธะฒะฐะตะผ ัะฐะนะผะตั ะฒะพ ะฒัะพัะพะน ัะฐะท, ะดะปั ะฟะพะฒัะพัะฝะพะน ะฟะพะฟััะบะธ ะฟะตัะตะดะฐัะธ
if (!connectionRecord.TimerSecondTry)
{
connectionRecord.WaitForPacketsTimer.Change(connectionRecord.ShortTimerPeriod, -1);
connectionRecord.TimerSecondTry = true;
return;
}
// ะตัะปะธ ะฟะพัะปะต ะดะฒัั
ะฟะพะฟััะพะบ ััะฐะฑะฐััะฒะฐะฝะธะน WaitForPacketTimer
// ะฝะต ัะดะฐะปะพัั ะฟะพะปััะธัั ะฟะฐะบะตัั - ะทะฐะฟััะบะฐะตะผ ัะฐะนะผะตั ะทะฐะฒะตััะตะฝะธั ัะพะตะดะธะฝะตะฝะธั
StartCloseWaitTimer(connectionRecord);
}
else if (/*ะฟัะธัะตะป ะฟะพัะปะตะดะฝะธะน ะฟะฐะบะตั ะธ ััะฟะตัะฝะฐั ะฟัะพะฒะตัะบะฐ */)
{
// ...
StartCloseWaitTimer(connectionRecord);
}
// ะตัะปะธ ack ะฝะฐ ะฑะปะพะบ ะฟะฐะบะตัะพะฒ ะฑัะป ะฟะพัะตััะฝ
else
{
if (!connectionRecord.TimerSecondTry)
{
// ะฟะพะฒัะพัะฝะพ ะพัััะปะฐะตะผ ack
connectionRecord.WaitForPacketsTimer.Change(connectionRecord.ShortTimerPeriod, -1);
connectionRecord.TimerSecondTry = true;
return;
}
// ะทะฐะฟััะบะฐะตะผ ัะฐะนะผะตั ะทะฐะฒะตััะตะฝะธั ัะพะตะดะธะฝะตะฝะธั
StartCloseWaitTimer(connectionRecord);
}
}
TimerSecondTry เชเชฒ เชชเชฐ เชธเซเช เชเชฐเซเชฒ เชเซ เชธเชพเชเซเช. เช เชเชฒ เชเชพเชฐเซเชฏเชเชพเชฐเซ เชเชพเชเชฎเชฐเชจเซ เชชเซเชจเชเชชเซเชฐเชพเชฐเชเชญ เชเชฐเชตเชพ เชฎเชพเชเซ เชเชตเชพเชฌเชฆเชพเชฐ เชเซ.
เชฎเซเชเชฒเชจเชพเชฐเชจเซ เชฌเชพเชเซเช, เชเชพเชฐเซเชฏเชเชพเชฐเซ เชเชพเชเชฎเชฐ เชชเชฃ เชเซเชฐเชฟเชเชฐ เชฅเชพเชฏ เชเซ เช
เชจเซ เชเซเชฒเซเชฒเซเช เชฎเซเชเชฒเซเชฒเซเช เชชเซเชเซเช เชซเชฐเซเชฅเซ เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซ เชเซ.
เชเชจเซเชเซเชถเชจ เชเซเชฒเซเช เชเชพเชเชฎเชฐ เชธเชเซเชทเชฎ เชเชฐเซ เชฐเชนเซเชฏเซเช เชเซ (เชธเซเชจเซเชกเชฟเชเชเชธเชพเชฏเชเชฒ เชธเซเชเซเช):
public override void ProcessPackets(ReliableUdpConnectionRecord connectionRecord)
{
// ...
// ะพัะฟัะฐะฒะปัะตะผ ะฟะพะฒัะพัะฝะพ ะฟะพัะปะตะดะฝะธะน ะฟะฐะบะตั
// ...
// ะฒะบะปััะฐะตะผ ัะฐะนะผะตั CloseWait โ ะดะปั ะพะถะธะดะฐะฝะธั ะฒะพัััะฐะฝะพะฒะปะตะฝะธั ัะพะตะดะธะฝะตะฝะธั ะธะปะธ ะตะณะพ ะทะฐะฒะตััะตะฝะธั
StartCloseWaitTimer(connectionRecord);
}
เชคเซ เชชเชเซ, เชเชเชเชเซเชเชเช เชเชจเซเชเซเชถเชจเชฎเชพเช เชเชจเซเชเซเชถเชจ เชเซเชฒเซเช เชเชพเชเชฎเชฐ เชถเชฐเซ เชฅเชพเชฏ เชเซ.
ReliableUdpState.StartCloseWaitTimer:
protected void StartCloseWaitTimer(ReliableUdpConnectionRecord connectionRecord)
{
if (connectionRecord.CloseWaitTimer != null)
connectionRecord.CloseWaitTimer.Change(connectionRecord.LongTimerPeriod, -1);
else
connectionRecord.CloseWaitTimer = new Timer(DisposeByTimeout, connectionRecord, connectionRecord.LongTimerPeriod, -1);
}
เชเชจเซเชเซเชถเชจ เชฌเชเชง เชเชพเชเชฎเชฐ เชธเชฎเชฏเชธเชฎเชพเชชเซเชคเชฟ เช เชตเชงเชฟ เชฎเซเชณเชญเซเชค เชฐเซเชคเซ 30 เชธเซเชเชจเซเชก เชเซ.
เชฅเซเชกเชพ เชธเชฎเชฏ เชชเชเซ, เชชเซเชฐเชพเชชเซเชคเชเชฐเซเชคเชพเชจเซ เชฌเชพเชเซ เชชเชฐเชจเซเช เชเชพเชฐเซเชฏเชเชพเชฐเซ เชเชพเชเชฎเชฐ เชซเชฐเซเชฅเซ เชซเชพเชฏเชฐ เชฅเชพเชฏ เชเซ, เชตเชฟเชจเชเชคเซเช เชซเชฐเซเชฅเซ เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซ เชเซ, เชคเซเชฏเชพเชฐเชฌเชพเชฆ เชเชตเชคเชพ เชเชจเซเชเซเชถเชจ เชฎเชพเชเซ เชเชจเซเชเซเชถเชจ เชเซเชฒเซเช เชเชพเชเชฎเชฐ เชถเชฐเซ เชฅเชพเชฏ เชเซ.
เชเซเชฏเชพเชฐเซ เชฌเชเชง เชเชพเชเชฎเชฐ เชซเชพเชฏเชฐ เชฅเชพเชฏ เชเซ, เชคเซเชฏเชพเชฐเซ เชฌเชเชจเซ เชเชจเซเชเซเชถเชจ เชฐเซเชเซเชฐเซเชกเซเชธเชจเชพ เชคเชฎเชพเชฎ เชธเชเชธเชพเชงเชจเซ เชชเซเชฐเชเชพเชถเชฟเชค เชฅเชพเชฏ เชเซ. เชชเซเชฐเซเชทเช เช
เชชเชธเซเชเซเชฐเซเชฎ เชเชชเซเชฒเชฟเชเซเชถเชจเชจเซ เชกเชฟเชฒเชฟเชตเชฐเซ เชจเชฟเชทเซเชซเชณเชคเชพเชจเซ เชเชพเชฃ เชเชฐเซ เชเซ (เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP API เชเซเช).
เชเชจเซเชเซเชถเชจ เชฐเซเชเซเชฐเซเชก เชธเชเชธเชพเชงเชจเซ เชฐเชฟเชฒเซเช เชเชฐเซ เชฐเชนเซเชฏเชพเช เชเซ:
public void Dispose()
{
try
{
System.Threading.Monitor.Enter(this.LockerReceive);
}
finally
{
Interlocked.Increment(ref this.IsDone);
if (WaitForPacketsTimer != null)
{
WaitForPacketsTimer.Dispose();
}
if (CloseWaitTimer != null)
{
CloseWaitTimer.Dispose();
}
byte[] stream;
Tcb.IncomingStreams.TryRemove(Key, out stream);
stream = null;
Tcb.OutcomingStreams.TryRemove(Key, out stream);
stream = null;
System.Threading.Monitor.Exit(this.LockerReceive);
}
}
เชเซเชกเชฎเชพเช เชตเชงเซ เชเชเชกเซ. เชกเซเชเชพ เชเซเชฐเชพเชจเซเชธเชซเชฐ เชชเซเชจเชเชธเซเชฅเชพเชชเชฟเชค เชเชฐเซ เชฐเชนเซเชฏเซเช เชเซ
เชชเซเชเซเช เชเซเชตเชพเช เชเชตเชพเชจเชพ เชเชฟเชธเซเชธเชพเชฎเชพเช เชกเซเชเชพ เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชฐเชฟเชเชตเชฐเซ เชกเชพเชฏเชพเชเซเชฐเชพเชฎ:
เชธเชฎเชฏเชธเชฎเชพเชชเซเชคเชฟ เชชเชฐ เชเชจเซเชเซเชถเชจ เชฌเชเชง เชเชฐเชตเชพ เชตเชฟเชถเซ เชชเชนเซเชฒเซเชฅเซ เช เชเชฐเซเชเชพ เชเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ, เชเซเชฏเชพเชฐเซ เชเชพเชฐเซเชฏเชเชพเชฐเซ เชเชพเชเชฎเชฐ เชธเชฎเชพเชชเซเชค เชฅเชพเชฏ เชเซ, เชคเซเชฏเชพเชฐเซ เชฐเซเชธเซเชตเชฐ เชเซเชตเชพเชฏเซเชฒเชพ เชชเซเชเซเชเซ เชฎเชพเชเซ เชคเชชเชพเชธ เชเชฐเชถเซ. เชชเซเชเซเช เชเซเชตเชพเช เชเชตเชพเชจเชพ เชเชฟเชธเซเชธเชพเชฎเชพเช, เชชเซเชฐเชพเชชเซเชคเชเชฐเซเชคเชพ เชธเซเชงเซ เชจ เชชเชนเซเชเชเซเชฒเชพ เชชเซเชเซเชเซเชจเซ เชธเชเชเซเชฏเชพเชจเซ เชฏเชพเชฆเซ เชคเซเชฏเชพเชฐ เชเชฐเชตเชพเชฎเชพเช เชเชตเชถเซ. เช เชจเชเชฌเชฐเซ เชเซเชเซเชเชธ เชเชจเซเชเซเชถเชจเชจเชพ LostPackets เชเชฐเซเชฎเชพเช เชฆเชพเชเชฒ เชเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ, เช
เชจเซ เชซเชฐเซเชฅเซ เชตเชฟเชคเชฐเชฃ เชฎเชพเชเซเชจเซ เชตเชฟเชจเชเชคเซเช เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซ เชเซ.
เชชเซเชเซเชเซ เชชเซเชจเชเชตเชฟเชคเชฐเชฟเชค เชเชฐเชตเชพ เชฎเชพเชเซ เชตเชฟเชจเชเชคเซเช เชฎเซเชเชฒเซ เชฐเชนเซเชฏเซเช เชเซ (เชเชธเซเชฎเซเชฌเชฒเชฟเชเช เชธเซเชเซเช):
public override void ProcessPackets(ReliableUdpConnectionRecord connectionRecord)
{
//...
if (!ReliableUdpStateTools.CheckForNoPacketLoss(connectionRecord, connectionRecord.IsLastPacketReceived != 0))
{
// ะตััั ะฟะพัะตััะฝะฝัะต ะฟะฐะบะตัั, ะพัััะปะฐะตะผ ะทะฐะฟัะพัั ะฝะฐ ะฝะธั
foreach (int seqNum in connectionRecord.LostPackets)
{
if (seqNum != 0)
{
ReliableUdpStateTools.SendAskForLostPacket(connectionRecord, seqNum);
}
}
// ...
}
}
เชชเซเชฐเซเชทเช เชซเชฐเซเชฅเซ เชกเชฟเชฒเชฟเชตเชฐเซ เชตเชฟเชจเชเชคเซ เชธเซเชตเซเชเชพเชฐเชถเซ เช
เชจเซ เชเซเชฎ เชฅเชฏเซเชฒ เชชเซเชเซเชเซ เชฎเซเชเชฒเชถเซ. เชคเซ เชจเซเชเชงเชตเซเช เชฏเซเชเซเชฏ เชเซ เชเซ เช เชเซเชทเชฃเซ เชชเซเชฐเซเชทเช เชชเชนเซเชฒเชพเชฅเซ เช เชเชจเซเชเซเชถเชจ เชเซเชฒเซเช เชเชพเชเชฎเชฐ เชถเชฐเซ เชเชฐเซ เชเซเชเซเชฏเซเช เชเซ เช
เชจเซ, เชเซเชฏเชพเชฐเซ เชตเชฟเชจเชเชคเซ เชชเซเชฐเชพเชชเซเชค เชฅเชพเชฏ เชเซ, เชคเซเชฏเชพเชฐเซ เชคเซ เชฐเซเชธเซเช เชฅเชพเชฏ เชเซ.
เชเซเชตเชพเชฏเซเชฒเชพ เชชเซเชเซเชเซ เชซเชฐเซเชฅเซ เชฎเซเชเชฒเซ เชฐเชนเซเชฏเชพ เชเซเช (เชธเซเชจเซเชกเชฟเชเชเชธเชพเชฏเชเชฒ เชธเซเชเซเช):
public override void ReceivePacket(ReliableUdpConnectionRecord connectionRecord, ReliableUdpHeader header, byte[] payload)
{
// ...
connectionRecord.WaitForPacketsTimer.Change(connectionRecord.ShortTimerPeriod, -1);
// ัะฑัะพั ัะฐะนะผะตัะฐ ะทะฐะบัััะธั ัะพะตะดะธะฝะตะฝะธั
if (connectionRecord.CloseWaitTimer != null)
connectionRecord.CloseWaitTimer.Change(-1, -1);
// ...
// ััะพ ะทะฐะฟัะพั ะฝะฐ ะฟะพะฒัะพัะฝัั ะฟะตัะตะดะฐัั โ ะพัะฟัะฐะฒะปัะตะผ ััะตะฑัะตะผัะน ะฟะฐะบะตั
else
ReliableUdpStateTools.SendPacket(connectionRecord, ReliableUdpStateTools.RetransmissionCreateUdpPayload(connectionRecord, header.PacketNumber));
}
เชฐเซเชธเซเชเช เชชเซเชเซเช (เชกเชพเชฏเชพเชเซเชฐเชพเชฎเชฎเชพเช เชชเซเชเซเช #3) เชเชจเชเชฎเชฟเชเช เชเชจเซเชเซเชถเชจ เชฆเซเชตเชพเชฐเชพ เชชเซเชฐเชพเชชเซเชค เชฅเชพเชฏ เชเซ. เชฐเซเชธเซเชต เชตเชฟเชจเซเชกเซ เชญเชฐเชพเช เชเช เชเซ เช
เชจเซ เชธเชพเชฎเชพเชจเซเชฏ เชกเซเชเชพ เชเซเชฐเชพเชจเซเชธเชฎเชฟเชถเชจ เชชเซเชจเชเชธเซเชฅเชพเชชเชฟเชค เชเซ เชเซ เชเซเชฎ เชคเซ เชเซเชตเชพ เชฎเชพเชเซ เชคเชชเชพเชธ เชเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ.
เชชเซเชฐเชพเชชเซเชค เชตเชฟเชเชกเซเชฎเชพเช เชนเชฟเช เชฎเชพเชเซ เชคเชชเชพเชธเซ เชฐเชนเซเชฏเซเช เชเซ (เชเชธเซเชฎเซเชฌเชฒเชฟเชเช เชธเซเชเซเช):
public override void ReceivePacket(ReliableUdpConnectionRecord connectionRecord, ReliableUdpHeader header, byte[] payload)
{
// ...
// ัะฒะตะปะธัะธะฒะฐะตะผ ััะตััะธะบ ะฟะฐะบะตัะพะฒ
connectionRecord.PacketCounter++;
// ะทะฐะฟะธััะฒะฐะตะผ ะฒ ะผะฐััะธะฒ ัะฟัะฐะฒะปะตะฝะธั ะพะบะฝะพะผ ัะตะบััะธะน ะฝะพะผะตั ะฟะฐะบะตัะฐ
connectionRecord.WindowControlArray[header.PacketNumber - connectionRecord.WindowLowerBound] = header.PacketNumber;
// ัััะฐะฝะฐะฒะปะธะฒะฐะตะผ ะฝะฐะธะฑะพะปััะธะน ะฟัะธัะตะดัะธะน ะฟะฐะบะตั
if (header.PacketNumber > connectionRecord.RcvCurrent)
connectionRecord.RcvCurrent = header.PacketNumber;
// ะฟะตัะตะทะฐะฟััะบะฐะผ ัะฐะนะผะตัั
connectionRecord.TimerSecondTry = false;
connectionRecord.WaitForPacketsTimer.Change(connectionRecord.ShortTimerPeriod, -1);
if (connectionRecord.CloseWaitTimer != null)
connectionRecord.CloseWaitTimer.Change(-1, -1);
// ...
// ะตัะปะธ ะฝะฐะผ ะฟัะธัะปะธ ะฒัะต ะฟะฐะบะตัั ะพะบะฝะฐ, ัะพ ัะฑัะฐััะฒะฐะตะผ ััะตััะธะบ
// ะธ ะฒัััะปะฐะตะผ ะฟะฐะบะตั ะฟะพะดัะฒะตัะถะดะตะฝะธะต
else if (connectionRecord.PacketCounter == connectionRecord.WindowSize)
{
// ัะฑัะฐััะฒะฐะตะผ ััะตััะธะบ.
connectionRecord.PacketCounter = 0;
// ัะดะฒะธะฝัะปะธ ะพะบะฝะพ ะฟะตัะตะดะฐัะธ
connectionRecord.WindowLowerBound += connectionRecord.WindowSize;
// ะพะฑะฝัะปะตะฝะธะต ะผะฐััะธะฒะฐ ัะฟัะฐะฒะปะตะฝะธั ะฟะตัะตะดะฐัะตะน
connectionRecord.WindowControlArray.Nullify();
ReliableUdpStateTools.SendAcknowledgePacket(connectionRecord);
}
// ...
}
เชตเชฟเชถเซเชตเชธเชจเซเชฏ UDP API
เชกเซเชเชพ เชเซเชฐเชพเชจเซเชธเชซเชฐ เชชเซเชฐเซเชเซเชเซเชฒ เชธเชพเชฅเซ เชเซเชฐเชฟเชฏเชพเชชเซเชฐเชคเชฟเชเซเชฐเชฟเชฏเชพ เชเชฐเชตเชพ เชฎเชพเชเซ, เชเช เชเซเชฒเซเชฒเซ เชตเชฟเชถเซเชตเชธเชจเซเชฏ Udp เชตเชฐเซเช เชเซ, เชเซ เชเซเชฐเชพเชจเซเชธเชซเชฐ เชเชเชเซเชฐเซเชฒ เชฌเซเชฒเซเช เชชเชฐ เชฐเซเชชเชฐ เชเซ. เช เชนเซเช เชตเชฐเซเชเชจเชพ เชธเซเชฅเซ เชฎเชนเชคเซเชตเชชเซเชฐเซเชฃ เชธเชญเซเชฏเซ เชเซ:
public sealed class ReliableUdp : IDisposable
{
// ะฟะพะปััะฐะตั ะปะพะบะฐะปัะฝัั ะบะพะฝะตัะฝัั ัะพัะบั
public IPEndPoint LocalEndpoint
// ัะพะทะดะฐะตั ัะบะทะตะผะฟะปัั ReliableUdp ะธ ะทะฐะฟััะบะฐะตั
// ะฟัะพัะปััะธะฒะฐะฝะธะต ะฒั
ะพะดััะธั
ะฟะฐะบะตัะพะฒ ะฝะฐ ัะบะฐะทะฐะฝะฝะพะผ IP ะฐะดัะตัะต
// ะธ ะฟะพััั. ะะฝะฐัะตะฝะธะต 0 ะดะปั ะฟะพััะฐ ะพะทะฝะฐัะฐะตั ะธัะฟะพะปัะทะพะฒะฐะฝะธะต
// ะดะธะฝะฐะผะธัะตัะบะธ ะฒัะดะตะปะตะฝะฝะพะณะพ ะฟะพััะฐ
public ReliableUdp(IPAddress localAddress, int port = 0)
// ะฟะพะดะฟะธัะบะฐ ะฝะฐ ะฟะพะปััะตะฝะธะต ะฒั
ะพะดััะธั
ัะพะพะฑัะตะฝะธะน
public ReliableUdpSubscribeObject SubscribeOnMessages(ReliableUdpMessageCallback callback, ReliableUdpMessageTypes messageType = ReliableUdpMessageTypes.Any, IPEndPoint ipEndPoint = null)
// ะพัะฟะธัะบะฐ ะพั ะฟะพะปััะตะฝะธั ัะพะพะฑัะตะฝะธะน
public void Unsubscribe(ReliableUdpSubscribeObject subscribeObject)
// ะฐัะธะฝั
ัะพะฝะฝะพ ะพัะฟัะฐะฒะธัั ัะพะพะฑัะตะฝะธะต
// ะัะธะผะตัะฐะฝะธะต: ัะพะฒะผะตััะธะผะพััั ั XP ะธ Server 2003 ะฝะต ัะตััะตััั, ั.ะบ. ะธัะฟะพะปัะทัะตััั .NET Framework 4.0
public Task<bool> SendMessageAsync(ReliableUdpMessage reliableUdpMessage, IPEndPoint remoteEndPoint, CancellationToken cToken)
// ะฝะฐัะฐัั ะฐัะธะฝั
ัะพะฝะฝัั ะพัะฟัะฐะฒะบั ัะพะพะฑัะตะฝะธั
public IAsyncResult BeginSendMessage(ReliableUdpMessage reliableUdpMessage, IPEndPoint remoteEndPoint, AsyncCallback asyncCallback, Object state)
// ะฟะพะปััะธัั ัะตะทัะปััะฐั ะฐัะธะฝั
ัะพะฝะฝะพะน ะพัะฟัะฐะฒะบะธ
public bool EndSendMessage(IAsyncResult asyncResult)
// ะพัะธััะธัั ัะตััััั
public void Dispose()
}
เชธเชฌเซเชธเซเชเซเชฐเชฟเชชเซเชถเชจ เชฆเซเชตเชพเชฐเชพ เชธเชเชฆเซเชถเชพเช เชชเซเชฐเชพเชชเซเชค เชฅเชพเชฏ เชเซ. เชเซเชฒเชฌเซเช เชชเชฆเซเชงเชคเชฟ เชฎเชพเชเซ เชชเซเชฐเชคเชฟเชจเชฟเชงเชฟ เชนเชธเซเชคเชพเชเซเชทเชฐ:
public delegate void ReliableUdpMessageCallback( ReliableUdpMessage reliableUdpMessage, IPEndPoint remoteClient );
เชธเชเชฆเซเชถ
public class ReliableUdpMessage
{
// ัะธะฟ ัะพะพะฑัะตะฝะธั, ะฟัะพััะพะต ะฟะตัะตัะธัะปะตะฝะธะต
public ReliableUdpMessageTypes Type { get; private set; }
// ะดะฐะฝะฝัะต ัะพะพะฑัะตะฝะธั
public byte[] Body { get; private set; }
// ะตัะปะธ ัััะฐะฝะพะฒะปะตะฝะพ ะฒ true โ ะผะตั
ะฐะฝะธะทะผ ะฟะพะดัะฒะตัะถะดะตะฝะธั ะดะพััะฐะฒะบะธ ะฑัะดะตั ะพัะบะปััะตะฝ
// ะดะปั ะฟะตัะตะดะฐัะธ ะบะพะฝะบัะตัะฝะพะณะพ ัะพะพะฑัะตะฝะธั
public bool NoAsk { get; private set; }
}
เชเซเชเซเชเชธ เชธเชเชฆเซเชถ เชชเซเชฐเชเชพเชฐ เช เชจเซ/เช เชฅเชตเชพ เชเซเชเซเชเชธ เชชเซเชฐเซเชทเชเชจเซ เชธเชฌเซเชธเซเชเซเชฐเชพเชเชฌ เชเชฐเชตเชพ เชฎเชพเชเซ, เชฌเซ เชตเซเชเชฒเซเชชเชฟเช เชชเชฐเชฟเชฎเชพเชฃเซเชจเซ เชเชชเชฏเซเช เชเชฐเชตเชพเชฎเชพเช เชเชตเซ เชเซ: ReliableUdpMessageTypes messageType เช เชจเซ IPEndPoint ipEndPoint.
เชธเชเชฆเซเชถเชจเชพ เชชเซเชฐเชเชพเชฐเซ:
public enum ReliableUdpMessageTypes : short
{
// ะัะฑะพะต
Any = 0,
// ะะฐะฟัะพั ะบ STUN server
StunRequest = 1,
// ะัะฒะตั ะพั STUN server
StunResponse = 2,
// ะะตัะตะดะฐัะฐ ัะฐะนะปะฐ
FileTransfer =3,
// ...
}
เชธเชเชฆเซเชถ เช เชธเซเชฎเซเชณ เชฐเซเชคเซ เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซ เชเซ; เช เชฎเชพเชเซ, เชชเซเชฐเซเชเซเชเซเชฒ เชเช เช เชธเซเชฎเซเชณ เชชเซเชฐเซเชเซเชฐเชพเชฎเชฟเชเช เชฎเซเชกเซเชฒ เชฒเชพเชเซ เชเชฐเซ เชเซ:
public IAsyncResult BeginSendMessage(ReliableUdpMessage reliableUdpMessage, IPEndPoint remoteEndPoint, AsyncCallback asyncCallback, Object state)
เชธเชเชฆเซเชถ เชฎเซเชเชฒเชตเชพเชจเซเช เชชเชฐเชฟเชฃเชพเชฎ เชธเชพเชเซเช เชนเชถเซ - เชเซ เชธเชเชฆเซเชถ เชธเชซเชณเชคเชพเชชเซเชฐเซเชตเช เชชเซเชฐเชพเชชเซเชคเชเชฐเซเชคเชพ เชธเซเชงเซ เชชเชนเซเชเชเซเชฏเซ เช เชจเซ เชเซเชเซ - เชเซ เชธเชฎเชฏเชธเชฎเชพเชชเซเชคเชฟ เชฆเซเชตเชพเชฐเชพ เชเชจเซเชเซเชถเชจ เชฌเชเชง เชเชฐเชตเชพเชฎเชพเช เชเชตเซเชฏเซเช เชนเซเชฏ เชคเซ:
public bool EndSendMessage(IAsyncResult asyncResult)
เชจเชฟเชทเซเชเชฐเซเชท
เช เชฒเซเชเชฎเชพเช เชเชฃเซเช เชตเชฐเซเชฃเชจ เชเชฐเชตเชพเชฎเชพเช เชเชตเซเชฏเซเช เชจเชฅเซ. เชฅเซเชฐเซเชก เชฎเซเชเชฟเชเช เชฎเชฟเชเซเชจเชฟเชเชฎเซเชธ, เช เชชเชตเชพเชฆ เช เชจเซ เชญเซเชฒ เชนเซเชจเซเชกเชฒเชฟเชเช, เช เชธเซเชฎเซเชณ เชธเชเชฆเซเชถ เชฎเซเชเชฒเชตเชพเชจเซ เชชเชฆเซเชงเชคเชฟเชเชจเซ เช เชฎเชฒ. เชชเชฐเชเชคเซ เชชเซเชฐเซเชเซเชเซเชฒเชจเซ เชฎเซเชเซเชฏ เชญเชพเช, เชชเซเชเซเชเซ เชชเชฐ เชชเซเชฐเชเซเชฐเชฟเชฏเชพ เชเชฐเชตเชพ เชฎเชพเชเซเชจเชพ เชคเชฐเซเชเชจเซเช เชตเชฐเซเชฃเชจ, เชเชจเซเชเซเชถเชจ เชธเซเชฅเชพเชชเชฟเชค เชเชฐเชตเซเช เช เชจเซ เชธเชฎเชฏเชธเชฎเชพเชชเซเชคเชฟเชจเซเช เชธเชเชเชพเชฒเชจ เชเชฐเชตเซเช, เชคเชฎเชพเชฐเชพ เชฎเชพเชเซ เชธเซเชชเชทเซเช เชนเซเชตเซเช เชเซเชเช.
เชตเชฟเชถเซเชตเชธเชจเซเชฏ เชกเชฟเชฒเชฟเชตเชฐเซ เชชเซเชฐเซเชเซเชเซเชฒเชจเซเช เชชเซเชฐเชฆเชฐเซเชถเชฟเชค เชธเชเชธเซเชเชฐเชฃ เช เชเชพเช เชจเชฟเชฐเซเชงเชพเชฐเชฟเชค เชเชฐเซเชฐเชฟเชฏเชพเชคเซเชจเซ เชชเชนเซเชเชเซ เชตเชณเชตเชพ เชฎเชพเชเซ เชชเซเชฐเชคเซเช เชฎเชเชฌเซเชค เช เชจเซ เชฒเชตเชเซเช เชเซ. เชชเชฐเชเชคเซ เชนเซเช เชเชฎเซเชฐเชตเชพ เชฎเชพเชเชเซ เชเซเช เชเซ เชตเชฐเซเชฃเชตเซเชฒ เช เชฎเชฒเซเชเชฐเชฃเชจเซ เชธเซเชงเชพเชฐเซ เชถเชเชพเชฏ เชเซ. เชเชฆเชพเชนเชฐเชฃ เชคเชฐเซเชเซ, เชฅเซเชฐเซเชชเซเช เชตเชงเชพเชฐเชตเชพ เช เชจเซ เชเชคเชฟเชถเซเชฒ เชฐเซเชคเซ เชเชพเชเชฎเชฐ เชชเซเชฐเชฟเชฏเชกเซเชธ เชฌเชฆเชฒเชตเชพ เชฎเชพเชเซ, เชชเซเชฐเซเชเซเชเซเชฒเชฎเชพเช เชธเซเชฒเชพเชเชกเชฟเชเช เชตเชฟเชจเซเชกเซ เช เชจเซ RTT เชเซเชตเซ เชฎเชฟเชเซเชจเชฟเชเชฎเซเชธ เชเชฎเซเชฐเซ เชถเชเชพเชฏ เชเซ, เชคเซ เชเชจเซเชเซเชถเชจ เชจเซเชกเซเชธ เชตเชเซเชเซ MTU เชจเชเซเชเซ เชเชฐเชตเชพ เชฎเชพเชเซเชจเซ เชฎเชฟเชเซเชจเชฟเชเชฎ เชฒเชพเชเซ เชเชฐเชตเชพ เชฎเชพเชเซ เชชเชฃ เชเชชเชฏเซเชเซ เชฅเชถเซ (เชชเชฐเชเชคเซ เชเซ เชฎเซเชเชพ เชธเชเชฆเซเชถเชพ เชฎเซเชเชฒเชตเชพเชฎเชพเช เชเชตเซ เชคเซ เช) .
เชคเชฎเชพเชฐเชพ เชงเซเชฏเชพเชจ เชฌเชฆเชฒ เชเชญเชพเชฐ, เชนเซเช เชคเชฎเชพเชฐเซ เชเชฟเชชเซเชชเชฃเซเช เช เชจเซ เชเชฟเชชเซเชชเชฃเซเชเชจเซ เชฐเชพเชน เชเซเชเช เชเซเช.
PS เชเซเช เชตเชฟเชเชคเซเชฎเชพเช เชฐเชธ เชงเชฐเชพเชตเซ เชเซ เช
เชฅเชตเชพ เชซเชเซเชค เชชเซเชฐเซเชเซเชเซเชฒเชจเซเช เชชเชฐเซเชเซเชทเชฃ เชเชฐเชตเชพ เชฎเชพเชเซ เชเซ เชคเซเชฎเชจเชพ เชฎเชพเชเซ, GitHube เชชเชฐเชจเชพ เชชเซเชฐเซเชเซเชเซเชเชจเซ เชฒเชฟเชเช:
เชเชชเชฏเซเชเซ เชฒเชฟเชเชเซเชธ เช
เชจเซ เชฒเซเชเซ
- TCP เชชเซเชฐเซเชเซเชเซเชฒ เชธเซเชชเชทเซเชเซเชเชฐเชฃ:
เช เชเชเซเชฐเซเชเซเชฎเชพเช ะธเชฐเชถเชฟเชฏเชจ - UDP เชชเซเชฐเซเชเซเชเซเชฒ เชธเซเชชเชทเซเชเซเชเชฐเชฃ:
เช เชเชเซเชฐเซเชเซเชฎเชพเช ะธเชฐเชถเชฟเชฏเชจ - RUDP เชชเซเชฐเซเชเซเชเซเชฒเชจเซ เชเชฐเซเชเชพ:
เชกเซเชฐเชพเชซเซเช-ietf-sigtran-reliable-udp-00 - เชตเชฟเชถเซเชตเชธเชจเซเชฏ เชกเซเชเชพ เชชเซเชฐเซเชเซเชเซเชฒ:
เชเชฐเชเชซเชธเซ 908 ะธเชเชฐเชเชซเชธเซ 1151 - UDP เชชเชฐ เชกเชฟเชฒเชฟเชตเชฐเซ เชเชจเซเชซเชฐเซเชฎเซเชถเชจเชจเซเช เชธเชฐเชณ เช
เชฎเชฒเซเชเชฐเชฃ:
.NET เช เชจเซ UDP เชธเชพเชฅเซ เชคเชฎเชพเชฐเชพ เชจเซเชเชตเชฐเซเชเชฟเชเช เชชเชฐ เชธเชเชชเซเชฐเซเชฃ เชจเชฟเชฏเชเชคเซเชฐเชฃ เชฒเซ - NAT เชเซเชฐเชพเชตเชฐเซเชธเชฒ เชฎเชฟเชเซเชจเชฟเชเชฎเซเชธเชจเซเช เชตเชฐเซเชฃเชจ เชเชฐเชคเซ เชฒเซเช:
เชชเซเช เชฐ-เชเซ-เชชเซเช เชฐ เชเซเชฎเซเชฏเซเชจเชฟเชเซเชถเชจ เชธเชฎเชเซเชฐ เชจเซเชเชตเชฐเซเช เชเชกเซเชฐเซเชธ เชเซเชฐเชพเชจเซเชธเชฒเซเชเชฐ - เช
เชธเซเชฎเซเชณ เชชเซเชฐเซเชเซเชฐเชพเชฎเชฟเชเช เชฎเซเชกเซเชฒเชจเซเช เช
เชฎเชฒเซเชเชฐเชฃ:
CLR เช เชธเชฟเชเชเซเชฐเซเชจเชธ เชชเซเชฐเซเชเซเชฐเชพเชฎเชฟเชเช เชฎเซเชกเชฒเชจเซ เช เชฎเชฒ ะธIAsyncResult เชกเชฟเชเชพเชเชจ เชชเซเชเชฐเซเชจเชจเซ เช เชฎเชฒ เชเซเชตเซ เชฐเซเชคเซ เชเชฐเชตเซ - เช
เชธเซเชฎเซเชณ เชชเซเชฐเซเชเซเชฐเชพเชฎเชฟเชเช เชฎเซเชกเชฒเชจเซ เชเชพเชฐเซเชฏ-เชเชงเชพเชฐเชฟเชค เช
เชธเซเชฎเซเชณ เชชเซเชเชฐเซเชจ (TAP เชฎเชพเช APM):
TPL เช เชจเซ เชชเชฐเชเชชเชฐเชพเชเชค .NET เช เชธเชฟเชเชเซเชฐเซเชจเชธ เชชเซเชฐเซเชเซเชฐเชพเชฎเชฟเชเช
เช เชจเซเชฏ เช เชธเชฟเชเชเซเชฐเซเชจเชธ เชชเซเชเชฐเซเชจ เช เชจเซ เชชเซเชฐเชเชพเชฐเซ เชธเชพเชฅเซ เชเชจเซเชเชฐเชเชช เชเชฐเซ
เช
เชชเชกเซเช: เชเชญเชพเชฐ
เชธเซเชฐเซเชธ: www.habr.com