Main Page   Modules   Data Structures   File List   Data Fields   Globals   Related Pages   Examples  

/opentcp/tcp.c

Go to the documentation of this file.
00001 /*
00002  *Copyright (c) 2000-2002 Viola Systems Ltd.
00003  *All rights reserved.
00004  *
00005  *Redistribution and use in source and binary forms, with or without 
00006  *modification, are permitted provided that the following conditions 
00007  *are met:
00008  *
00009  *1. Redistributions of source code must retain the above copyright 
00010  *notice, this list of conditions and the following disclaimer.
00011  *
00012  *2. Redistributions in binary form must reproduce the above copyright 
00013  *notice, this list of conditions and the following disclaimer in the 
00014  *documentation and/or other materials provided with the distribution.
00015  *
00016  *3. The end-user documentation included with the redistribution, if 
00017  *any, must include the following acknowledgment:
00018  *      "This product includes software developed by Viola 
00019  *      Systems (http://www.violasystems.com/)."
00020  *
00021  *Alternately, this acknowledgment may appear in the software itself, 
00022  *if and wherever such third-party acknowledgments normally appear.
00023  *
00024  *4. The names "OpenTCP" and "Viola Systems" must not be used to 
00025  *endorse or promote products derived from this software without prior 
00026  *written permission. For written permission, please contact 
00027  *opentcp@opentcp.org.
00028  *
00029  *5. Products derived from this software may not be called "OpenTCP", 
00030  *nor may "OpenTCP" appear in their name, without prior written 
00031  *permission of the Viola Systems Ltd.
00032  *
00033  *THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESSED OR IMPLIED 
00034  *WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 
00035  *MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 
00036  *IN NO EVENT SHALL VIOLA SYSTEMS LTD. OR ITS CONTRIBUTORS BE LIABLE 
00037  *FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 
00038  *CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 
00039  *SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR 
00040  *BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 
00041  *WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE 
00042  *OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, 
00043  *EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00044  *====================================================================
00045  *
00046  *OpenTCP is the unified open source TCP/IP stack available on a series 
00047  *of 8/16-bit microcontrollers, please see <http://www.opentcp.org>.
00048  *
00049  *For more information on how to network-enable your devices, or how to 
00050  *obtain commercial technical support for OpenTCP, please see 
00051  *<http://www.violasystems.com/>.
00052  */
00053 
00085 #include <inet/debug.h>
00086 #include <inet/datatypes.h>
00087 #include <inet/timers.h>
00088 #include <inet/ethernet.h>
00089 #include <inet/ip.h>
00090 #include <inet/tcp_ip.h>
00091 #include <inet/system.h>
00092 
00102 struct tcp_frame received_tcp_packet;
00103 
00118 struct tcb tcp_socket[NO_OF_TCPSOCKETS + 1]; 
00119 
00120 UINT8 tcp_tempbuf[MIN_TCP_HLEN + 1]; 
00123 /***********************************************************************/
00124 /*******        TCP API functions                                                                       ********/
00125 /***********************************************************************/
00126 
00155 INT8 tcp_getsocket (UINT8 soctype, UINT8 tos, UINT16 tout, INT32 (*listener)(INT8, UINT8, UINT32, UINT32) )
00156 {
00157         INT8 i;
00158         struct tcb* soc;
00159         
00160         if( NO_OF_TCPSOCKETS < 0 )
00161                 return(-1);
00162         
00163         if( NO_OF_TCPSOCKETS == 0 )
00164                 return(-1);
00165         
00166         if( (soctype != TCP_TYPE_SERVER) &&
00167                 (soctype != TCP_TYPE_CLIENT) &&
00168                 (soctype != TCP_TYPE_CLIENT_SERVER) &&
00169                 (soctype != TCP_TYPE_NONE)                              ) {
00170                 TCP_DEBUGOUT("Invalid socket type requested\r\n");
00171                 return(-1);
00172         }
00173         
00174         if(listener == 0) {
00175                 TCP_DEBUGOUT("ERROR:Event listener function not specified\r\n");
00176                 return(-1);
00177         }
00178         
00179         TCP_DEBUGOUT("Searching for free TCP socket...\r\n");
00180         
00181         for(i=0; i < NO_OF_TCPSOCKETS; i++)     {
00182                 soc = &tcp_socket[i];                   /* Get Socket   */
00183         
00184                 if(soc->state == TCP_STATE_FREE) {
00185                         /* We found it  */
00186                         
00187                         TCP_DEBUGOUT("Free socket found\r\n");
00188                         
00189                         soc->state = TCP_STATE_RESERVED;
00190                         soc->type = soctype;
00191                         soc->tos = tos;
00192                         soc->event_listener = listener;
00193                         soc->rem_ip = 0;
00194                         soc->remport = 0;
00195                         soc->locport = 0;
00196                         soc->flags = 0;
00197                         soc->tout = tout*TIMERTIC;
00198                         
00199                         return(i);
00200                 }
00201         
00202         }
00203         
00204         /* We are there so no socket found      */
00205         
00206         TCP_DEBUGOUT("No socket found\r\n");
00207         return(-1);
00208 
00209 }
00210 
00228 INT8 tcp_releasesocket (INT8 sochandle)
00229 {
00230         struct tcb* soc;
00231         
00232         if( NO_OF_TCPSOCKETS < 0 )
00233                 return(-1);
00234         
00235         if( NO_OF_TCPSOCKETS == 0 )
00236                 return(-1);
00237         
00238         if( sochandle > NO_OF_TCPSOCKETS ) {
00239                 TCP_DEBUGOUT("Socket handle non-valid\r\n");
00240                 return(-1);
00241         }
00242         
00243         if( sochandle < 0 ) {
00244                 TCP_DEBUGOUT("Socket handle non-valid\r\n");
00245                 return(-1);
00246         }
00247         
00248         soc = &tcp_socket[sochandle];           /* Get referense        */
00249         
00250         if( (soc->state != TCP_STATE_FREE) &&
00251                 (soc->state != TCP_STATE_RESERVED) &&
00252                 (soc->state != TCP_STATE_CLOSED)                ) {
00253                 TCP_DEBUGOUT("Socket is not on valid state to be released\r\n");
00254                 return(-1);
00255         }
00256         
00257         /* We are there so all OK       */
00258         
00259         soc->state = TCP_STATE_FREE;
00260         soc->type = TCP_TYPE_NONE;
00261         soc->tos = 0;
00262         soc->event_listener = 0;
00263         soc->rem_ip = 0;
00264         soc->remport = 0;
00265         soc->locport = 0;
00266         soc->flags = 0;
00267         
00268         return(sochandle);
00269 
00270 }
00271 
00290 INT8 tcp_listen (INT8 sochandle, UINT16 port)
00291 {
00292         struct tcb* soc;
00293 
00294         if( NO_OF_TCPSOCKETS < 0 )
00295                 return(-1);
00296         
00297         if( NO_OF_TCPSOCKETS == 0 )
00298                 return(-1);
00299         
00300         if( sochandle > NO_OF_TCPSOCKETS ) {
00301                 TCP_DEBUGOUT("Socket handle non-valid\r\n");
00302                 return(-1);
00303         }
00304         
00305         if( sochandle < 0 ) {
00306                 TCP_DEBUGOUT("Socket handle non-valid\r\n");
00307                 return(-1);
00308         }
00309         
00310         soc = &tcp_socket[sochandle];           /* Get referense        */
00311                 
00312         if( (soc->type & TCP_TYPE_SERVER) == 0 ) {
00313                 TCP_DEBUGOUT("Socket has no server properties\r\n");
00314                 return(-1);
00315         }
00316         
00317         if( soc->event_listener == 0) {
00318                 TCP_DEBUGOUT("ERROR:No event listener function specified\r\n");
00319                 return(-1);
00320         }
00321         
00322         
00323         if( (soc->state != TCP_STATE_RESERVED) &&
00324                 (soc->state != TCP_STATE_LISTENING)     &&
00325                 (soc->state != TCP_STATE_CLOSED) &&             
00326                 (soc->state != TCP_STATE_TIMED_WAIT)            ) {
00327                 TCP_DEBUGOUT("Not possible to listen, socket on connected state\r\n");
00328                 return(-1);
00329         
00330         }
00331         
00332                         
00333         /* Init socket          */
00334                                 
00335         soc->state = TCP_STATE_LISTENING;
00336         /*soc->type = TCP_TYPE_SERVER;*/
00337         soc->flags = 0;
00338         soc->rem_ip = 0;
00339         soc->remport = 0;
00340         soc->locport = port;
00341         soc->send_unacked = 0;
00342         soc->myflags = 0;
00343         soc->send_next = 0xFFFFFFFF;
00344         soc->send_mtu = TCP_DEF_MTU;
00345         soc->receive_next = 0;
00346         soc->retries_left = 0;
00347                         
00348         TCP_DEBUGOUT("TCP listening socket created\r\n");
00349                         
00350         return(sochandle);
00351 
00352 }
00353 
00354 
00377 INT8 tcp_connect (INT8 sochandle, UINT32 ip, UINT16 rport, UINT16 myport )
00378 {
00379         struct tcb* soc;
00380         
00381         TCP_DEBUGOUT("FUNCTION: tcp_connect\r\n");
00382 
00383         if( NO_OF_TCPSOCKETS < 0 )
00384                 return(-1);
00385         
00386         if( NO_OF_TCPSOCKETS == 0 )
00387                 return(-1);
00388         
00389         if( sochandle > NO_OF_TCPSOCKETS ) {
00390                 TCP_DEBUGOUT("Socket handle non-valid\r\n");
00391                 return(-1);
00392         }
00393         
00394         if( sochandle < 0 ) {
00395                 TCP_DEBUGOUT("Socket handle non-valid\r\n");
00396                 return(-1);
00397         }
00398         
00399         /* Is the local port defined    */
00400         
00401         if( myport == 0 )
00402                 myport = tcp_getfreeport();
00403         
00404         if( myport == 0 )
00405                 return(-1);
00406         
00407         soc = &tcp_socket[sochandle];           /* Get referense        */
00408         
00409         /* Do we have client properties?        */
00410         
00411         if( (soc->type & TCP_TYPE_CLIENT) == 0 ) {
00412                 TCP_DEBUGOUT("Socket has no client properties\r\n");
00413                 return(-1);
00414         }
00415         
00416         if( soc->event_listener == 0) {
00417                 TCP_DEBUGOUT("ERROR:No event listener function specified\r\n");
00418                 return(-1);
00419         }
00420         
00421         /* Are we on LISTENING, RESERVED or CLOSED state        */
00422         
00423         if( (soc->state != TCP_STATE_RESERVED) &&
00424                 (soc->state != TCP_STATE_LISTENING) &&
00425                 (soc->state != TCP_STATE_CLOSED)                ) {
00426                 TCP_DEBUGOUT("Socket on unvalid state to initialize CONNECT\r\n");
00427                 return(-1);
00428         }
00429         
00430         /* Then just set parameters and send SYN        */
00431         
00432         soc->rem_ip = ip;
00433         soc->remport = rport;
00434         soc->locport = myport;
00435         soc->flags = 0;
00436         soc->send_mtu = TCP_DEF_MTU;
00437         
00438         /* get initial sequence number  */
00439         
00440         soc->send_unacked = tcp_initseq(); 
00441         soc->send_next = soc->send_unacked + 1;
00442         soc->myflags = TCP_FLAG_SYN;
00443         tcp_sendcontrol(sochandle);
00444         tcp_newstate(soc, TCP_STATE_SYN_SENT);
00445         
00446         return(sochandle);
00447 }
00448 
00449 
00450 
00481 INT16 tcp_send (INT8 sockethandle, UINT8* buf, UINT16 blen, UINT16 dlen)
00482 {
00483         struct tcb* soc;
00484         UINT8 i;
00485 
00486         
00487         TCP_DEBUGOUT("Entering to send TCP data packet\r\n");
00488         
00489         kick_WD();
00490         
00491         if( sockethandle < 0 ) {
00492                 TCP_DEBUGOUT("ERROR:Socket Handle not valid (<0)\r\n");
00493                 return(-1);
00494         }
00495         
00496         if( sockethandle > NO_OF_TCPSOCKETS ) {
00497                 TCP_DEBUGOUT("ERROR:Socket Handle not valid (>NO_OF_TCPSOCKETS)\r\n");
00498                 return(-1);
00499         }
00500         
00501         soc = &tcp_socket[sockethandle];                                /* Get socket   */
00502         
00503         if(soc->state != TCP_STATE_CONNECTED) {
00504                 TCP_DEBUGOUT("TCP is not connected!!\r\n");
00505                 return(-1);
00506         }
00507         
00508         if(soc->send_unacked != soc->send_next) {
00509                 TCP_DEBUGOUT("TCP contains unacked data, cannot send more\r\n");
00510                 return(-1);
00511         }
00512         
00513         if( dlen > blen )
00514                 dlen = blen;
00515         
00516         if(dlen + MIN_TCP_HLEN > soc->send_mtu) {
00517                 if(soc->send_mtu > MIN_TCP_HLEN)
00518                         dlen = soc->send_mtu - MIN_TCP_HLEN;
00519                 else
00520                         return(-1);
00521         }
00522         
00523         soc->send_next += dlen;
00524         
00525         soc->myflags = TCP_FLAG_ACK | TCP_FLAG_PUSH;
00526         process_tcp_out(sockethandle, buf - MIN_TCP_HLEN, blen + MIN_TCP_HLEN + 1, dlen);
00527         
00528         return(dlen);
00529 }
00530 
00531 
00549 INT8 tcp_close (INT8 sochandle)
00550 {
00551         struct tcb* soc;
00552         
00553         TCP_DEBUGOUT("FUNCTION: tcp_close\r\n");
00554 
00555         if( NO_OF_TCPSOCKETS < 0 )
00556                 return(-1);
00557         
00558         if( NO_OF_TCPSOCKETS == 0 )
00559                 return(-1);
00560         
00561         if( sochandle > NO_OF_TCPSOCKETS ) {
00562                 TCP_DEBUGOUT("Socket handle non-valid\r\n");
00563                 return(-1);
00564         }
00565         
00566         if( sochandle < 0 ) {
00567                 TCP_DEBUGOUT("Socket handle non-valid\r\n");
00568                 return(-1);
00569         }
00570         
00571         soc = &tcp_socket[sochandle];           /* Get referense        */      
00572         
00573         switch(soc->state) {
00574                 case TCP_STATE_LISTENING:
00575                         tcp_newstate(soc, TCP_STATE_CLOSED);
00576                         break;
00577                 
00578                 case TCP_STATE_SYN_RECEIVED:
00579                         soc->myflags = TCP_FLAG_ACK | TCP_FLAG_FIN;
00580                         soc->send_unacked++;
00581                         soc->send_next++;
00582                         tcp_sendcontrol(sochandle);
00583                         tcp_newstate(soc, TCP_STATE_FINW1);
00584                         break;
00585                 
00586                 case TCP_STATE_SYN_SENT:
00587                 
00588                         tcp_newstate(soc, TCP_STATE_CLOSED);
00589                 
00590                         break;
00591                 
00592                 case TCP_STATE_FINW1:
00593                 case TCP_STATE_FINW2:
00594                 case TCP_STATE_CLOSING:
00595                 case TCP_STATE_TIMED_WAIT:
00596                 case TCP_STATE_LAST_ACK:
00597                 
00598                         /* We are closing already       */
00599                         
00600                         break;
00601                 
00602                 case TCP_STATE_CONNECTED:
00603                 
00604                         /* Is there unacked data?       */
00605                         
00606                         if(soc->send_unacked == soc->send_next ) {
00607                                 /* There is no unacked data     */
00608                                 
00609                                 soc->myflags = TCP_FLAG_ACK | TCP_FLAG_FIN;
00610                                 soc->send_next++;
00611                                 tcp_sendcontrol(sochandle);
00612                                 tcp_newstate(soc, TCP_STATE_FINW1);                             
00613                         } else {
00614                                 /* Can't do much but raise pollable flag to soc->flags          */
00615                                 /* and process it on tcp_poll                                                           */
00616                                 
00617                                 soc->flags |= TCP_INTFLAGS_CLOSEPENDING;
00618                                 
00619                                 
00620                                 return(sochandle);
00621                         }
00622                 
00623                         break;
00624         
00625                 default:
00626                         return(-1);
00627         }
00628         
00629         return(sochandle);
00630 
00631 }
00632 
00633 
00634 
00648 INT8 tcp_getstate (INT8 sochandle)
00649 {
00650         struct tcb* soc;
00651 
00652         if( NO_OF_TCPSOCKETS < 0 )
00653                 return(-1);
00654         
00655         if( NO_OF_TCPSOCKETS == 0 )
00656                 return(-1);
00657         
00658         if( sochandle > NO_OF_TCPSOCKETS ) {
00659                 TCP_DEBUGOUT("Socket handle non-valid\r\n");
00660                 return(-1);
00661         }
00662         
00663         if( sochandle < 0 ) {
00664                 TCP_DEBUGOUT("Socket handle non-valid\r\n");
00665                 return(-1);
00666         }
00667         
00668         soc = &tcp_socket[sochandle];           /* Get referense        */      
00669 
00670         return(soc->state);
00671 
00672 }
00673 
00674 
00690 INT16 tcp_checksend (INT8 sochandle)
00691 {
00692         struct tcb* soc;
00693 
00694         if( NO_OF_TCPSOCKETS < 0 )
00695                 return(-1);
00696         
00697         if( NO_OF_TCPSOCKETS == 0 )
00698                 return(-1);
00699         
00700         if( sochandle > NO_OF_TCPSOCKETS ) {
00701                 TCP_DEBUGOUT("Socket handle non-valid\r\n");
00702                 return(-1);
00703         }
00704         
00705         soc = &tcp_socket[sochandle];           /* Get referense        */      
00706         
00707         if(soc->state != TCP_STATE_CONNECTED)
00708                 return(-1);
00709 
00710         if(soc->send_unacked == soc->send_next)
00711                 return(soc->send_mtu);
00712         
00713         return(-1);
00714 
00715 
00716 }
00717 
00718 
00719 
00736 INT8 tcp_abort (INT8 sochandle)
00737 {
00738         struct tcb* soc;
00739         
00740         TCP_DEBUGOUT("FUNCTION: tcp_abort\r\n");
00741 
00742         if( NO_OF_TCPSOCKETS < 0 )
00743                 return(-1);
00744         
00745         if( NO_OF_TCPSOCKETS == 0 )
00746                 return(-1);
00747         
00748         if( sochandle > NO_OF_TCPSOCKETS ) {
00749                 TCP_DEBUGOUT("Socket handle non-valid\r\n");
00750                 return(-1);
00751         }
00752         
00753         if( sochandle < 0 ) {
00754                 TCP_DEBUGOUT("Socket handle non-valid\r\n");
00755                 return(-1);
00756         }
00757         
00758         soc = &tcp_socket[sochandle];           /* Get referense        */      
00759 
00760         switch (soc->state)     {
00761                 case TCP_STATE_FREE:
00762                         return(-1);
00763                         
00764                 case TCP_STATE_RESERVED:
00765                 case TCP_STATE_CLOSED:
00766                         return(sochandle);
00767                 
00768                 case TCP_STATE_TIMED_WAIT:
00769                 case TCP_STATE_LISTENING:
00770                         tcp_newstate(soc, TCP_STATE_CLOSED);
00771                         return(sochandle);
00772                 
00773                 case TCP_STATE_SYN_SENT:
00774                 case TCP_STATE_SYN_RECEIVED:
00775                 case TCP_STATE_CONNECTED:
00776                 case TCP_STATE_FINW1:
00777                 case TCP_STATE_FINW2:
00778                 case TCP_STATE_CLOSING:
00779                 case TCP_STATE_LAST_ACK:
00780                 
00781                         soc->myflags = TCP_FLAG_RESET;
00782                         tcp_sendcontrol(sochandle);
00783                         tcp_newstate(soc, TCP_STATE_CLOSED);
00784                         return(sochandle);
00785                         
00786                 default:
00787                         return(-1);
00788         }
00789         
00790 
00791 }
00792 
00793 
00794 
00808 void tcp_poll (void)
00809 {
00810         struct tcb* soc;
00811         static UINT8 handle = 0;
00812         UINT8 i;
00813         INT32 temp;
00814         UINT8 old_retries;
00815         
00816         for(i=0; i < NO_OF_TCPSOCKETS; i++ ) {
00817                 
00818                 if(handle > NO_OF_TCPSOCKETS)
00819                         handle = 0;
00820 
00821                 soc = &tcp_socket[handle];
00822                 
00823                 switch(soc->state) {
00824                         case TCP_STATE_FREE:
00825                         case TCP_STATE_RESERVED:
00826                         case TCP_STATE_CLOSED:
00827                         case TCP_STATE_LISTENING:
00828                                 
00829                                 break;
00830                                 
00831                         case TCP_STATE_CONNECTED:
00832                         
00833                                 /* In CONNECTED State we have                                   */ 
00834                                 /* something to do only if we have unacked data */
00835                                 /* or if connection has been IDLE too long or   */
00836                                 /* unserved close is isuued by user                             */
00837                                 
00838                                 /*if(soc->send_next > soc->send_unacked)
00839                                         temp = soc->send_next - soc->send_unacked;
00840                                 else
00841                                         temp = soc->send_unacked - soc->send_next;
00842                                 */
00843                                 
00844                                 temp = soc->send_next - soc->send_unacked;
00845                                 
00846                                 /* Unserved Close?                      */
00847                                 
00848                                 if(soc->flags & TCP_INTFLAGS_CLOSEPENDING) {
00849                                         /* Can we send the close now    */
00850                                         
00851                                         if(temp == 0) {
00852                                                 soc->myflags = TCP_FLAG_ACK | TCP_FLAG_FIN;
00853                                                 soc->send_next++;
00854                                                 tcp_sendcontrol(handle);
00855                                                 tcp_newstate(soc, TCP_STATE_FINW1);     
00856                                                 soc->flags ^= TCP_INTFLAGS_CLOSEPENDING;
00857                                                 
00858                                                 handle++;
00859                                                 
00860                                                 return;         
00861                                                 
00862                                         }
00863                                 }
00864                                 
00865                                 /* Socket timeout?                      */
00866                                 
00867                                 if(check_timer(soc->persist_timerh) == 0) {
00868                                 
00869                                         soc->myflags = TCP_FLAG_ACK | TCP_FLAG_FIN;
00870                                         soc->send_next++;
00871                                         tcp_sendcontrol(handle);
00872                                         tcp_newstate(soc, TCP_STATE_FINW1);     
00873                                         
00874                                         /* Inform application   */
00875                                         
00876                                         soc->event_listener(handle, TCP_EVENT_CLOSE, soc->rem_ip, soc->remport);
00877                                         
00878                                         handle++;
00879                 
00880                                         return;                 
00881                                 }       
00882                                 
00883                                 /* Is there unacked data?       */
00884                                 
00885                                 if(temp == 0)
00886                                         break;
00887                                 
00888                                 /* Is there timeout?                                    */
00889                                 
00890                                 if( check_timer(soc->retransmit_timerh) != 0 )
00891                                         break;
00892                                 
00893                                 /* De we have retries left                              */
00894                                 
00895                                 if(soc->retries_left == 0) {
00896                                         /* No retries, must reset       */
00897                                         
00898                                         TCP_DEBUGOUT("Retries used up, resetting\r\n");
00899                                         
00900                                         soc->myflags = TCP_FLAG_RESET;
00901                                         tcp_sendcontrol(handle);
00902                                         
00903                                         /* Inform application   */
00904 
00905                                         soc->event_listener(handle, TCP_EVENT_ABORT, soc->rem_ip, soc->remport);
00906                                 
00907                                         if(soc->type & TCP_TYPE_SERVER )
00908                                                 tcp_newstate(soc, TCP_STATE_LISTENING);
00909                                         else
00910                                                 tcp_newstate(soc, TCP_STATE_CLOSED);
00911                                         
00912                                         handle++;
00913                 
00914                                         return;                                                                         
00915                                 }
00916                                 
00917                                 soc->retries_left--;
00918                                 init_timer(soc->retransmit_timerh, TCP_DEF_RETRY_TOUT*TIMERTIC);
00919                                                                 
00920                                 /* Yep, there is unacked data                   */
00921                                 /* Application should send the old data */
00922                                 
00923                                 if(temp>soc->send_mtu)
00924                                         temp = soc->send_mtu;
00925                                 
00926                                 /* Rewind Send Next because the send process will adjust it                     */
00927                                 /* So cheat the tcp_send to think there is no unacked data                      */
00928                                 
00929                                 soc->send_next = soc->send_unacked;
00930                                 
00931                                 /* tcp_send will set the retiries_left to maximum but this is           */
00932                                 /* retransmitting already so we need to retain it in order to           */
00933                                 /* avoid dead-lock                                                                                                      */
00934                                 
00935                                 old_retries = soc->retries_left;
00936                                 
00937                                 temp = soc->event_listener(handle, TCP_EVENT_REGENERATE, (UINT32)temp, 0);
00938                         
00939                                 soc->retries_left = old_retries;
00940                         
00941                                 if(temp <= 0) {
00942                                         
00943                                         /* No data by application, must be something wrong      */
00944                                         soc->myflags = TCP_FLAG_RESET;
00945                                         tcp_sendcontrol(handle);
00946                                         
00947                                         /* Inform application   */
00948 
00949                                         soc->event_listener(handle, TCP_EVENT_ABORT, soc->rem_ip, soc->remport);
00950                                                                         
00951                                         if(soc->type & TCP_TYPE_SERVER )
00952                                                 tcp_newstate(soc, TCP_STATE_LISTENING);
00953                                         else
00954                                                 tcp_newstate(soc, TCP_STATE_CLOSED);
00955                                         
00956                                         handle++;
00957                 
00958                                         return;                                 
00959                                         
00960                                 }
00961                                 
00962                                 /* Application has send data    */
00963                                 
00964                                 handle++;
00965                 
00966                                 return;
00967                                 
00968                         
00969                         case TCP_STATE_SYN_SENT:
00970                         case TCP_STATE_SYN_RECEIVED:
00971                         
00972                                 /* Is there timeout?    */
00973                                 if( check_timer(soc->retransmit_timerh) != 0 )
00974                                         break;
00975                                         
00976                                 TCP_DEBUGOUT("Timeout\r\n");
00977                                         
00978                                 /* Yep, timeout. Is there reties left?  */
00979                                 if( soc->retries_left ) {
00980                                         soc->retries_left--;
00981                                         if(soc->state == TCP_STATE_SYN_SENT)
00982                                                 init_timer(soc->retransmit_timerh, TCP_SYN_RETRY_TOUT*TIMERTIC);
00983                                         else
00984                                                 init_timer(soc->retransmit_timerh, TCP_DEF_RETRY_TOUT*TIMERTIC);
00985 
00986                                         tcp_sendcontrol(handle);
00987                                         
00988                                         handle++;
00989                 
00990                                         return;                         
00991                                 } else {
00992                                         /* Retries used up      */
00993                                         TCP_DEBUGOUT("Retries used up, resetting\r\n");
00994                                         
00995                                         if(soc->type & TCP_TYPE_SERVER )
00996                                                 tcp_newstate(soc, TCP_STATE_LISTENING);
00997                                         else
00998                                                 tcp_newstate(soc, TCP_STATE_CLOSED);
00999                                         
01000                                         soc->myflags = TCP_FLAG_RESET;
01001                                         tcp_sendcontrol(handle);
01002                                         
01003                                         /* Inform application   */
01004 
01005                                         soc->event_listener(handle, TCP_EVENT_ABORT, soc->rem_ip, soc->remport);
01006                                         
01007                                         handle++;
01008                 
01009                                         return;
01010                                 }
01011                                 
01012                                 break;
01013                                 
01014                         case TCP_STATE_TIMED_WAIT:
01015                                 
01016                                 /* Is there timeout?    */
01017                                 
01018                                 if( check_timer(soc->retransmit_timerh) != 0 )
01019                                         break;
01020                                         
01021                                 TCP_DEBUGOUT("Timeout\r\n");
01022                                 
01023                                 if(soc->retries_left) {
01024                                         soc->retries_left--;
01025                                         init_timer(soc->retransmit_timerh, TCP_DEF_RETRY_TOUT*TIMERTIC);
01026                                         break;
01027                                 }
01028                                 
01029                                 if(soc->type & TCP_TYPE_SERVER )
01030                                         tcp_newstate(soc, TCP_STATE_LISTENING);
01031                                 else
01032                                         tcp_newstate(soc, TCP_STATE_CLOSED);
01033                                         
01034                                 break;
01035                         
01036                         case TCP_STATE_LAST_ACK:
01037                         case TCP_STATE_FINW1:
01038                         case TCP_STATE_CLOSING:
01039                         
01040                                 /* Is there timeout?    */
01041                                 
01042                                 if( check_timer(soc->retransmit_timerh) != 0 )
01043                                         break;
01044                                         
01045                                 TCP_DEBUGOUT("Timeout\r\n");            
01046                                                 
01047                                 /* Yep, timeout. Is there reties left?  */
01048                                 
01049                                 if( soc->retries_left ) {
01050                                         soc->retries_left--;
01051                                         init_timer(soc->retransmit_timerh, TCP_DEF_RETRY_TOUT*TIMERTIC);
01052                                         soc->myflags = TCP_FLAG_FIN | TCP_FLAG_ACK;
01053                                         tcp_sendcontrol(handle);
01054                                         
01055                                         handle++;
01056                 
01057 
01058                                         return;                         
01059                                 } else {
01060                                         /* Retries used up      */
01061                                         TCP_DEBUGOUT("Retries used up, resetting\r\n");
01062                                         
01063                                         if(soc->type & TCP_TYPE_SERVER )
01064                                                 tcp_newstate(soc, TCP_STATE_LISTENING);
01065                                         else
01066                                                 tcp_newstate(soc, TCP_STATE_CLOSED);
01067                                         
01068                                         soc->myflags = TCP_FLAG_RESET;
01069                                         tcp_sendcontrol(handle);
01070                                         
01071                                         /* Inform application   */
01072 
01073                                         soc->event_listener(handle, TCP_EVENT_ABORT, soc->rem_ip, soc->remport);
01074                                         
01075                                         handle++;
01076                 
01077                                         return;
01078                                 }                       
01079                                 
01080                                 break;
01081                         
01082                         case TCP_STATE_FINW2:
01083                         
01084                                 /* Is there timeout?    */
01085                                 
01086                                 if( check_timer(soc->retransmit_timerh) != 0 )
01087                                         break;
01088                                         
01089                                 TCP_DEBUGOUT("Timeout\r\n");            
01090                                                 
01091                                 /* Yep, timeout. Is there reties left?  */
01092                                 
01093                                 if( soc->retries_left ) {
01094                                         /* Still keep waiting for FIN   */
01095                                 
01096                                         soc->retries_left--;
01097                                         init_timer(soc->retransmit_timerh, TCP_DEF_RETRY_TOUT*TIMERTIC);
01098                                         break;                  
01099                                 } else {
01100                                         /* Retries used up      */
01101                                         TCP_DEBUGOUT("Retries used up, resetting\r\n");
01102                                         
01103                                         if(soc->type & TCP_TYPE_SERVER )
01104                                                 tcp_newstate(soc, TCP_STATE_LISTENING);
01105                                         else
01106                                                 tcp_newstate(soc, TCP_STATE_CLOSED);
01107                                         
01108                                         soc->myflags = TCP_FLAG_RESET;
01109                                         tcp_sendcontrol(handle);
01110                                         
01111                                         /* Inform application   */
01112 
01113                                         soc->event_listener(handle, TCP_EVENT_ABORT, soc->rem_ip, soc->remport);
01114                                 
01115                                         handle++;
01116                 
01117                                         return;
01118                                 }       
01119                                 
01120                                 break;
01121                         
01122                         default:
01123                                 break;  
01124                         
01125                 }
01126                 
01127                 /* Go to next socket if there was no event      */
01128                 
01129                 handle++;
01130                 
01131         }
01132         
01133 }
01134 
01135 
01136 
01154 INT8 tcp_init (void)
01155 {
01156         UINT16 i;
01157         INT16 h;
01158         struct tcb* soc;
01159         
01160         if( NO_OF_TCPSOCKETS < 0 )
01161                 return(-1);
01162         
01163         if( NO_OF_TCPSOCKETS == 0 )
01164                 return(0);
01165         
01166         TCP_DEBUGOUT("Initializing TCP");
01167         
01168         for(i=0; i < NO_OF_TCPSOCKETS; i++) {
01169                 soc = &tcp_socket[i];                   /* Get Socket   */
01170                 h = -1;
01171                 
01172                 soc->state = TCP_STATE_FREE;
01173                 soc->type = TCP_TYPE_NONE;
01174                 soc->flags = 0;
01175                 soc->rem_ip = 0;
01176                 soc->remport = 0;
01177                 soc->locport = 0;
01178                 soc->myflags = 0;
01179                 soc->send_mtu = TCP_DEF_MTU;
01180                 soc->tos = 0;
01181                 soc->tout = 0;
01182                 soc->event_listener = 0;
01183                 
01184                 /* Reserve Timers       */
01185                 
01186                 h = get_timer();
01187                 
01188                 /*
01189                 if( h < 0 ) {
01190                         TCP_DEBUGOUT("\n\rERROR:Error getting timer for TCP Socket!\n\r");
01191                         return(-1);
01192                 }
01193                 */
01194                 
01195                 init_timer(h,0);                                        /* No timeout   */
01196                 
01197                 soc->persist_timerh = h;
01198                 
01199                 h = get_timer();
01200                 
01201                 /*
01202                 if( h < 0 ) {
01203                         TCP_DEBUGOUT("\n\rERROR:Error getting timer for TCP Socket!\n\r");
01204                         return(-1);
01205                 }
01206                 */
01207                 
01208                 init_timer(h,0);                                        /* No timeout   */
01209                 
01210                 soc->retransmit_timerh = h;
01211                 
01212                 soc->retries_left = 0;           
01213                 
01214                 TCP_DEBUGOUT(".");
01215                 
01216         
01217         }
01218         
01219         TCP_DEBUGOUT("\n\rTCP Initialized\n\r");
01220         
01221         /* Return number of sockets initialized */
01222         
01223         return(i+1);
01224         
01225 
01226 }
01227 
01228 
01229 
01230 
01231 /*******************************************************************************/
01232 /*******        TCP Internal functions                                                                          ********/
01233 /*******************************************************************************/
01234 
01235 
01250 INT16 process_tcp_in (struct ip_frame* frame, UINT16 len)
01251 {
01252         struct tcb* soc;
01253         UINT16 hlen;
01254         UINT8 olen;
01255         UINT16 dlen;
01256         UINT32 diff;
01257         UINT16 i;
01258         INT8 sochandle; 
01259         INT16 temp;
01260         
01261         /* Is this TCP? */
01262         
01263         TCP_DEBUGOUT("Processing TCP...\n\r");
01264         
01265         if( frame->protocol != IP_TCP ) {
01266                 TCP_DEBUGOUT("ERROR: The protocol is not TCP\n\r");
01267                 return(-1);
01268         }
01269         
01270         /* Calculate checksum for received packet       */
01271 
01272         
01273         NETWORK_RECEIVE_INITIALIZE(frame->buf_index);
01274         
01275         if( tcp_check_cs(frame, len) == 1) {
01276                 TCP_DEBUGOUT("TCP Checksum OK\n\r");
01277         } else {
01278                 TCP_DEBUGOUT("ERROR:TCP Checksum failed\r\n");
01279                 return(-1);
01280         } 
01281 
01282         /* Get the header       */
01283         
01284         NETWORK_RECEIVE_INITIALIZE(frame->buf_index);
01285         
01286         received_tcp_packet.sport = ((UINT16)RECEIVE_NETWORK_B()) << 8;
01287         received_tcp_packet.sport |= RECEIVE_NETWORK_B();
01288         
01289         received_tcp_packet.dport = ((UINT16)RECEIVE_NETWORK_B()) << 8;
01290         received_tcp_packet.dport |= RECEIVE_NETWORK_B();
01291         
01292         received_tcp_packet.seqno = (((UINT32)RECEIVE_NETWORK_B()) << 24);
01293         received_tcp_packet.seqno |= (((UINT32)RECEIVE_NETWORK_B()) << 16);
01294         received_tcp_packet.seqno |= (((UINT32)RECEIVE_NETWORK_B()) << 8);
01295         received_tcp_packet.seqno |= RECEIVE_NETWORK_B();
01296         
01297         received_tcp_packet.ackno = (((UINT32)RECEIVE_NETWORK_B()) << 24);
01298         received_tcp_packet.ackno |= (((UINT32)RECEIVE_NETWORK_B()) << 16);
01299         received_tcp_packet.ackno |= (((UINT32)RECEIVE_NETWORK_B()) << 8);
01300         received_tcp_packet.ackno |= RECEIVE_NETWORK_B();
01301 
01302         received_tcp_packet.hlen_flags = ((UINT16)RECEIVE_NETWORK_B()) << 8;
01303         received_tcp_packet.hlen_flags |= RECEIVE_NETWORK_B();
01304         
01305         received_tcp_packet.window = ((UINT16)RECEIVE_NETWORK_B()) << 8;
01306         received_tcp_packet.window |= RECEIVE_NETWORK_B();
01307         
01308         received_tcp_packet.checksum = ((UINT16)RECEIVE_NETWORK_B()) << 8;
01309         received_tcp_packet.checksum |= RECEIVE_NETWORK_B();
01310         
01311         received_tcp_packet.urgent = ((UINT16)RECEIVE_NETWORK_B()) << 8;
01312         received_tcp_packet.urgent |= RECEIVE_NETWORK_B();
01313         
01314         /* Little check for options     */
01315         
01316         hlen = received_tcp_packet.hlen_flags & 0xF000;
01317         hlen >>= 10;
01318         
01319         if( hlen < MIN_TCP_HLEN ) {
01320                 TCP_DEBUGOUT("ERROR: Received TCP Header too short\r\n");
01321                 return(-1);
01322         }
01323         
01324         if(hlen == MIN_TCP_HLEN)
01325                 TCP_DEBUGOUT("TCP does not contain options\r\n");
01326         
01327         olen = hlen - MIN_TCP_HLEN;
01328         
01329         if( olen > MAX_TCP_OPTLEN ) {
01330                 TCP_DEBUGOUT("ERROR: Received TCP header contains too long option field\r\n");
01331                 return(-1);
01332         }
01333         
01334         /* Calculate data length        */
01335         
01336         if( hlen > len ) {
01337                 TCP_DEBUGOUT("ERROR: TCP header longer than packet\r\n");
01338                 return(-1);
01339         }
01340         
01341         dlen = len - hlen - olen;
01342         
01343         /* Get options (if any) */
01344         
01345         for(i=0; i<olen;i++)
01346                 received_tcp_packet.opt[i] = RECEIVE_NETWORK_B();
01347                 
01348         /* Try to find rigth socket to process with             */
01349         
01350         sochandle = tcp_mapsocket(frame, &received_tcp_packet);
01351         
01352         if(sochandle < 0) {
01353                 TCP_DEBUGOUT("ERROR: Processing TCP packet failed\r\n");
01354                 tcp_sendreset(&received_tcp_packet, frame->sip);
01355                 return(-1);
01356         }
01357         
01358         received_tcp_packet.buf_index = frame->buf_index + hlen;
01359         NETWORK_RECEIVE_INITIALIZE(received_tcp_packet.buf_index);
01360         
01361         
01362         
01363         /* Get socket reference */
01364         
01365         soc = &tcp_socket[sochandle];
01366         
01367         /* Process the packet on TCP State Machine              */
01368         
01369         switch(soc->state) {
01370                 case TCP_STATE_CONNECTED:
01371                 
01372                         TCP_DEBUGOUT("CONNECTED State\r\n");
01373                         
01374                         /* Check for RESET      */
01375                         
01376                         if(received_tcp_packet.hlen_flags & TCP_FLAG_RESET)     {
01377                                 TCP_DEBUGOUT("ERROR:Reset received\r\n");
01378 
01379                                 /* Inform application   */
01380 
01381                                 soc->event_listener(sochandle, TCP_EVENT_ABORT, soc->rem_ip, soc->remport);                             
01382                                 
01383                                 if(soc->type & TCP_TYPE_SERVER)
01384                                         tcp_newstate(soc, TCP_STATE_LISTENING);
01385                                 else
01386                                         tcp_newstate(soc, TCP_STATE_CLOSED);
01387                                         
01388                                 return(-1);
01389                         }
01390                         
01391                         /* Check for SYN (If the peer didn't get our SYN+ACK or ACK)    */
01392                         
01393                         if( received_tcp_packet.hlen_flags & TCP_FLAG_SYN )     {
01394                                 /* Is it the SYN+ACK we have already ACKed but maybe ACK lost?  */
01395                                 
01396                                 if( received_tcp_packet.hlen_flags & TCP_FLAG_ACK )     {
01397                                         /* It's SYN+ACK but how about sequence  */
01398                                         
01399                                         if( (received_tcp_packet.seqno + 1) == soc->receive_next ) {
01400                                         
01401                                                 if( received_tcp_packet.ackno == soc->send_next ) {
01402                                                 
01403                                                         TCP_DEBUGOUT("Received SYN+ACK again\r\n");
01404                                                         
01405                                                         /* ACK the SYN  */
01406                                                         soc->myflags = TCP_FLAG_ACK;
01407                                                         tcp_sendcontrol(sochandle);
01408                                                         return(0);
01409                                                 }
01410                                                 
01411                                         }
01412                                 
01413                                  /* It is maybe SYN again so it haven't get our SYN + ACK       */
01414                                  /* Let our retransmission handle it                                            */
01415                                  
01416                                  return(0);
01417                                 
01418                                 
01419                                 }
01420                         
01421                         }
01422                         
01423                         /* Do we have unacked data?             */
01424                         
01425                         if( soc->send_unacked != soc->send_next ) {
01426                         
01427                                 /* Yep, is the ACK valid?       */
01428                                 
01429                                 if( (received_tcp_packet.hlen_flags & TCP_FLAG_ACK) == 0) {
01430                                 
01431                                         TCP_DEBUGOUT("Packet without ACK and unacked data. Packet not processed\r\n");
01432                                         return(0);
01433                                 }
01434                                 
01435                                 if( received_tcp_packet.ackno == soc->send_next ) {
01436                                 
01437                                         /* We don't have unacked data now       */
01438                                 
01439                                         soc->send_unacked = soc->send_next;
01440                                 
01441                                         /* Inform application   */
01442                                 
01443                                         soc->event_listener(sochandle, TCP_EVENT_ACK, soc->rem_ip, soc->remport);
01444                                 
01445                                 }
01446 
01447                         
01448                         }
01449                         
01450                         /* Is the sequence OK   */
01451                         
01452                         if(soc->receive_next != received_tcp_packet.seqno)
01453                         {
01454                                 /* Out of range, inform what we except  */
01455                         
01456                                 DEBUGOUT("Too big sequence number received\r\n");
01457                                 
01458                                 soc->myflags = TCP_FLAG_ACK;
01459                                 tcp_sendcontrol(sochandle);
01460                                 return(0);
01461                         }
01462                         
01463                         /* Generate data event to application   */
01464                                 
01465                         soc->event_listener(sochandle, TCP_EVENT_DATA, dlen, 0);
01466                                 
01467                         soc->receive_next += dlen;                      
01468                                         
01469                         /* Is the FIN flag set? */
01470                         
01471                         if( received_tcp_packet.hlen_flags & TCP_FLAG_FIN )     {
01472                                 TCP_DEBUGOUT("Other end want's to close\r\n");
01473                                 
01474                                 /* Inform application if we don't have unacked data     */
01475                                 
01476                                 if( soc->send_unacked == soc->send_next) {
01477                                 
01478                                         soc->event_listener(sochandle, TCP_EVENT_CLOSE, soc->rem_ip, soc->remport);
01479                                 
01480                                         /* ACK FIN and set our own FIN  */
01481                                 
01482                                         soc->receive_next++;
01483                                         soc->send_next++;
01484                                         soc->myflags = TCP_FLAG_ACK | TCP_FLAG_FIN;
01485                                 
01486                                         tcp_newstate(soc, TCP_STATE_LAST_ACK);
01487                                         tcp_sendcontrol(sochandle);
01488                                 
01489                                         return(0);
01490                                 }
01491                         }
01492                         
01493                         /* ACK the data if there was it */
01494                         
01495                         if(dlen) {
01496                                 soc->myflags = TCP_FLAG_ACK;
01497                                 tcp_sendcontrol(sochandle);
01498                         }
01499                         
01500                         tcp_newstate(soc, TCP_STATE_CONNECTED);                 
01501                         
01502 
01503                         return(0);
01504                         
01505                 
01506                         break;
01507         
01508                 case TCP_STATE_FREE:
01509                         
01510                         /* Reset connection     */
01511                         tcp_sendreset(&received_tcp_packet, frame->sip);
01512                         return(-1);
01513                 
01514                         break;
01515                 
01516                 case TCP_STATE_CLOSED:
01517                         
01518                         /* Reset connection     */
01519                         tcp_sendreset(&received_tcp_packet, frame->sip);
01520                         return(-1);             
01521                 
01522                         break;
01523                 
01524                 case TCP_STATE_LISTENING:
01525                 
01526                         TCP_DEBUGOUT("LISTENING State...\r\n");
01527                 
01528                         /* Check Flags  */
01529                         
01530                         if(received_tcp_packet.hlen_flags & TCP_FLAG_RESET) {
01531                                 TCP_DEBUGOUT("ERROR:Reset received\r\n");
01532                                 tcp_newstate(soc, TCP_STATE_LISTENING);
01533                                 return(-1);
01534                         }
01535                         
01536                         if(received_tcp_packet.hlen_flags & TCP_FLAG_ACK) {
01537                                 TCP_DEBUGOUT("ERROR:Ack received\r\n");
01538                                 tcp_newstate(soc, TCP_STATE_LISTENING);
01539                                 /* Reset connection     */
01540                                 tcp_sendreset(&received_tcp_packet, frame->sip);
01541                                 return(-1);     
01542                         }
01543                         
01544                         if((received_tcp_packet.hlen_flags & TCP_FLAG_SYN) == 0) {
01545                                 TCP_DEBUGOUT("ERROR:No SYN set on packet\r\n");
01546                                 tcp_newstate(soc, TCP_STATE_LISTENING);
01547                                 /* Reset connection     */
01548                                 tcp_sendreset(&received_tcp_packet, frame->sip);
01549                                 return(-1);
01550                         }
01551                         
01552                         /* OK, SYN received     */
01553                         
01554                         /* Inform application and see if accepted       */
01555                         
01556                         temp = (INT16)soc->event_listener(sochandle, TCP_EVENT_CONREQ, soc->rem_ip, soc->remport);
01557                         
01558                         if( temp == -1) {
01559                                 TCP_DEBUGOUT("Application disregarded connection request\r\n");
01560                                 tcp_sendreset(&received_tcp_packet, frame->sip);
01561                                 return(-1);
01562                         }
01563                         
01564                         if( temp == -2 ) {
01565                                 TCP_DEBUGOUT("Application wants to think about accepting conreq\r\n");
01566                                 return(1);
01567                         }
01568                         
01569                         /* The connection request was accepted  */
01570                         
01571                         TCP_DEBUGOUT("Next state SYN_RECEIVED\r\n");
01572                         if(soc->flags & TCP_INTFLAGS_CLOSEPENDING)
01573                                 soc->flags ^= TCP_INTFLAGS_CLOSEPENDING;
01574                         tcp_newstate(soc, TCP_STATE_SYN_RECEIVED);
01575                         soc->receive_next = received_tcp_packet.seqno + 1;      /* Ack SYN              */
01576                         soc->send_unacked = tcp_initseq();
01577                         
01578                         soc->myflags = TCP_FLAG_SYN | TCP_FLAG_ACK;
01579                         tcp_sendcontrol(sochandle);
01580                         soc->send_next = soc->send_unacked + 1;
01581                         
01582                         return(1);
01583                         
01584                         break;
01585                         
01586                 case TCP_STATE_SYN_RECEIVED:
01587                 
01588                         TCP_DEBUGOUT("SYN_RECEIVED State...\r\n");
01589                         
01590                         /* Check Flags  */
01591                         
01592                         if(received_tcp_packet.hlen_flags & TCP_FLAG_RESET)     {
01593                                 TCP_DEBUGOUT("ERROR:Reset received\r\n");
01594                                 
01595                                 /* Inform application   */
01596                                 
01597                                 soc->event_listener(sochandle, TCP_EVENT_ABORT, soc->rem_ip, soc->remport);
01598                                 
01599                                 if(soc->type & TCP_TYPE_SERVER)
01600                                         tcp_newstate(soc, TCP_STATE_LISTENING);
01601                                 else
01602                                         tcp_newstate(soc, TCP_STATE_CLOSED);
01603                                         
01604                                 return(-1);
01605                         }
01606                         
01607                         /* Is it SYN+ACK (if we are the because of simultaneous open)   */
01608                         
01609                         if( (received_tcp_packet.hlen_flags & TCP_FLAG_SYN) &&
01610                                 (received_tcp_packet.hlen_flags & TCP_FLAG_ACK) ) {                     
01611                                 
01612                                 if( received_tcp_packet.ackno != soc->send_next ) {
01613                                         TCP_DEBUGOUT("SYN+ACK received but wrong Ack\n\r");
01614                                         return(-1);
01615                                 }
01616                                 
01617                                 TCP_DEBUGOUT("SYN+ACK received, this side established\n\r");
01618                                 
01619                                 /* Get peer's seq number        */
01620                                 
01621                                 soc->receive_next =  received_tcp_packet.seqno;
01622                                 soc->receive_next++;                                                    /* ACK SYN      */
01623                                 
01624                                 /* We have no unacked data      */
01625                                 
01626                                 soc->send_unacked = soc->send_next;
01627                                 
01628                                 tcp_newstate(soc, TCP_STATE_CONNECTED);
01629                                 soc->myflags = TCP_FLAG_ACK;
01630                                 tcp_sendcontrol(sochandle);
01631                                 
01632                                 /* Inform application   */
01633                                 
01634                                 soc->event_listener(sochandle, TCP_EVENT_CONNECTED, soc->rem_ip, soc->remport);
01635                                 
01636                                 return(0);                                      
01637                                                                 
01638                         }
01639                         
01640                         /* Is it ACK?           */
01641                         
01642                         if( received_tcp_packet.hlen_flags & TCP_FLAG_ACK )     {
01643                                 if( received_tcp_packet.ackno != soc->send_next ) {
01644                                         TCP_DEBUGOUT("ACK received but wrong Ack\n\r");
01645                                         return(-1);
01646                                 }
01647                                 
01648                                 if( received_tcp_packet.seqno != soc->receive_next ) {
01649                                         TCP_DEBUGOUT("ACK received but Wrong SEQ number\n\r");
01650                                         return(-1);
01651                                 }
01652                                 
01653                                 TCP_DEBUGOUT("ACK received, this side CONNECTED\r\n");
01654                                 
01655                                 /* We have no unacked data      */
01656                                 
01657                                 soc->send_unacked = soc->send_next;
01658                                 
01659                                 tcp_newstate(soc, TCP_STATE_CONNECTED);
01660 
01661                                 /* Inform application   */
01662                                 
01663                                 soc->event_listener(sochandle, TCP_EVENT_CONNECTED, soc->rem_ip, soc->remport);
01664                                                                 
01665                                 return(0);
01666                                         
01667                         }
01668                         
01669                         /* Is it SYN?           */
01670                         
01671                         if( received_tcp_packet.hlen_flags & TCP_FLAG_SYN ) {
01672                                 TCP_DEBUGOUT("Repeated SYN\r\n");
01673                                 return(0);
01674                         }
01675                         
01676                         /* We didn't understood this one, keep on trying but info with RESET    */
01677                         
01678                         TCP_DEBUGOUT("Unrecognized packet\n\r");
01679                         
01680                         tcp_sendreset(&received_tcp_packet, frame->sip);
01681                         
01682                         return(-1);
01683                         
01684                         break;
01685                         
01686                 case TCP_STATE_SYN_SENT:
01687                 
01688                         TCP_DEBUGOUT("SYN_SENT State\r\n");
01689                         
01690                         /* Check for RESET      */
01691                         
01692                         if(received_tcp_packet.hlen_flags & TCP_FLAG_RESET) {
01693                                 TCP_DEBUGOUT("ERROR:Reset received\r\n");
01694                                 
01695                                 /* Inform application   */
01696 
01697                                 soc->event_listener(sochandle, TCP_EVENT_ABORT, soc->rem_ip, soc->remport);
01698                                                                 
01699                                 if(soc->type & TCP_TYPE_SERVER)
01700                                         tcp_newstate(soc, TCP_STATE_LISTENING);
01701                                 else
01702                                         tcp_newstate(soc, TCP_STATE_CLOSED);
01703                                         
01704                                 return(-1);
01705                         }
01706                         
01707                         /* Is it SYN+ACK?       */
01708                         
01709                         if( (received_tcp_packet.hlen_flags & TCP_FLAG_SYN) &&
01710                                 (received_tcp_packet.hlen_flags & TCP_FLAG_ACK) ) {
01711                                 /* Rigth ACK?   */
01712                                 
01713                                 if( received_tcp_packet.ackno != soc->send_next ) {
01714                                         TCP_DEBUGOUT("SYN+ACK received but wrong Ack\n\r");
01715                                         return(-1);
01716                                 }
01717                                 
01718                                 TCP_DEBUGOUT("SYN+ACK received, this side established\n\r");
01719                                 
01720                                 /* Get peer's seq number        */
01721                                 
01722                                 soc->receive_next =  received_tcp_packet.seqno;
01723                                 soc->receive_next++;                                                    /* ACK SYN      */
01724                                 
01725                                 /* We have no unacked data      */
01726                                 
01727                                 soc->send_unacked = soc->send_next;
01728                                 
01729                                 tcp_newstate(soc, TCP_STATE_CONNECTED);
01730                                 soc->myflags = TCP_FLAG_ACK;
01731                                 tcp_sendcontrol(sochandle);
01732                                 
01733                                 /* Inform application   */
01734 
01735                                 soc->event_listener(sochandle, TCP_EVENT_CONNECTED, soc->rem_ip, soc->remport);
01736                                                                 
01737                                 return(0);                      
01738                                 
01739                         }
01740                         
01741                         /* Is it SYN (simultaneous open)        */
01742                         
01743                         if(received_tcp_packet.hlen_flags & TCP_FLAG_SYN) {
01744                                 TCP_DEBUGOUT("Simultaneous open, next SYN_RECEIVED\r\n");
01745                         
01746                                 /* Get peer's seq number        */
01747                                 
01748                                 soc->receive_next =  received_tcp_packet.seqno;
01749                                 soc->receive_next++;                                                    /* ACK SYN      */                              
01750                                 
01751                                 tcp_newstate(soc, TCP_STATE_SYN_RECEIVED);
01752                                 soc->myflags = TCP_FLAG_SYN | TCP_FLAG_ACK;
01753                                 tcp_sendcontrol(sochandle);
01754                                 
01755                                 return(0);
01756                         
01757                         }
01758                         
01759                         /* This is something we didn't understood, maybe the other peer has     */
01760                         /* still old connection on or something                                                         */
01761                         TCP_DEBUGOUT("TCP packet out of nowhere received...\r\n");
01762                         tcp_sendreset(&received_tcp_packet, frame->sip);
01763                         
01764                         return(-1);
01765                 
01766                         break;
01767                 
01768                 case TCP_STATE_FINW1:
01769                 
01770                         TCP_DEBUGOUT("FINW1 State\r\n");
01771                         
01772                         /* Check for RESET      */
01773                         
01774                         if(received_tcp_packet.hlen_flags & TCP_FLAG_RESET) {
01775                                 TCP_DEBUGOUT("ERROR:Reset received\r\n");
01776                                 
01777                                 /* Inform application   */
01778 
01779                                 soc->event_listener(sochandle, TCP_EVENT_ABORT, soc->rem_ip, soc->remport);
01780                                                                 
01781                                 if(soc->type & TCP_TYPE_SERVER)
01782                                         tcp_newstate(soc, TCP_STATE_LISTENING);
01783                                 else
01784                                         tcp_newstate(soc, TCP_STATE_CLOSED);
01785                                         
01786                                 return(-1);
01787                         }
01788                         
01789                         /* Is it FIN+ACK?                       */
01790                         
01791                         if( (received_tcp_packet.hlen_flags & TCP_FLAG_FIN) &&
01792                                 (received_tcp_packet.hlen_flags & TCP_FLAG_ACK) ) {
01793                                 /* Rigth ACK?   */
01794                                 
01795                                 if( received_tcp_packet.ackno != soc->send_next ) {
01796                                         TCP_DEBUGOUT("FIN+ACK received but wrong Ack\n\r");
01797                                         return(-1);
01798                                 }
01799                                 
01800                                 TCP_DEBUGOUT("FIN+ACK received, next TIMED_WAIT\n\r");
01801                                 
01802                                 /* ACK FIN and all data */
01803                                 
01804                                 soc->receive_next = received_tcp_packet.seqno;
01805                                 soc->receive_next++;
01806                                 soc->receive_next += dlen;
01807                                 
01808                                 /* We have no unacked data      */
01809                                 
01810                                 soc->send_unacked = soc->send_next;
01811                                 
01812                                 tcp_newstate(soc, TCP_STATE_TIMED_WAIT);
01813                                 soc->myflags = TCP_FLAG_ACK;
01814                                 tcp_sendcontrol(sochandle);
01815                                                         
01816                                 return(0);
01817                         
01818                         }
01819                         
01820                         /* Is it just FIN       */
01821                         
01822                         if( received_tcp_packet.hlen_flags & TCP_FLAG_FIN       ) {
01823                                 
01824                                 TCP_DEBUGOUT("Simultaneous close, next CLOSING\n\r");
01825                                 
01826                                 /* ACK FIN and all data */
01827                                 
01828                                 soc->receive_next = received_tcp_packet.seqno;
01829                                 soc->receive_next++;
01830                                 soc->receive_next += dlen;
01831                                 
01832                                 tcp_newstate(soc, TCP_STATE_CLOSING);
01833                                 soc->myflags = TCP_FLAG_ACK;
01834                                 tcp_sendcontrol(sochandle);                     
01835                                 return(0);
01836                         
01837                         }                       
01838                         
01839                         /* Is it just ACK?      */
01840                         
01841                         if( received_tcp_packet.hlen_flags & TCP_FLAG_ACK       ) {
01842                                 /* Rigth ACK?   */
01843                                 
01844                                 if( received_tcp_packet.ackno != soc->send_next ) {
01845                                         TCP_DEBUGOUT("ACK received but wrong Ack\n\r");
01846                                         return(-1);
01847                                 }
01848                                 
01849                                 TCP_DEBUGOUT("Our FIN is ACKed but peer don't agree to disconnect yet\r\n");
01850                                 TCP_DEBUGOUT("Next FINW2\r\n");
01851                                 
01852                                 /* We have no unacked data      */
01853                                 
01854                                 soc->send_unacked = soc->send_next;
01855                                 
01856                                 tcp_newstate(soc, TCP_STATE_FINW2);
01857                                 
01858                                 return(0);
01859                                                         
01860                         }
01861                                                 
01862                         break;
01863                         
01864                 case TCP_STATE_FINW2:
01865                 
01866                         TCP_DEBUGOUT("FINW2 State\r\n");
01867                         
01868                         /* Check for RESET      */
01869                         
01870                         if(received_tcp_packet.hlen_flags & TCP_FLAG_RESET) {
01871                                 TCP_DEBUGOUT("ERROR:Reset received\r\n");
01872                                 
01873                                 /* Inform application   */
01874 
01875                                 soc->event_listener(sochandle, TCP_EVENT_ABORT, soc->rem_ip, soc->remport);                             
01876                                 
01877                                 if(soc->type & TCP_TYPE_SERVER)
01878                                         tcp_newstate(soc, TCP_STATE_LISTENING);
01879                                 else
01880                                         tcp_newstate(soc, TCP_STATE_CLOSED);
01881                                         
01882                                 return(-1);
01883                         }                       
01884                 
01885                         /* Do we finally get FIN?       */
01886                 
01887                         if( received_tcp_packet.hlen_flags & TCP_FLAG_FIN       ) {
01888                                 
01889                                 TCP_DEBUGOUT("FIN received, next TIMED_WAIT\n\r");
01890                                 
01891                                 /* ACK FIN and all data */
01892                                 
01893                                 soc->receive_next = received_tcp_packet.seqno;
01894                                 soc->receive_next++;
01895                                 soc->receive_next += dlen;
01896                                 
01897                                 tcp_newstate(soc, TCP_STATE_TIMED_WAIT);
01898                                 soc->myflags = TCP_FLAG_ACK;
01899                                 tcp_sendcontrol(sochandle);                     
01900                                 return(0);
01901                         
01902                         }               
01903                 
01904                         break;
01905                         
01906                 case TCP_STATE_CLOSING:
01907                 
01908                         TCP_DEBUGOUT("CLOSING State...\r\n");
01909                         
01910                         /* Check for RESET      */
01911                         
01912                         if(received_tcp_packet.hlen_flags & TCP_FLAG_RESET)     {
01913                                 TCP_DEBUGOUT("ERROR:Reset received\r\n");
01914 
01915                                 /* Inform application   */
01916 
01917                                 soc->event_listener(sochandle, TCP_EVENT_ABORT, soc->rem_ip, soc->remport);                             
01918                                 
01919                                 if(soc->type & TCP_TYPE_SERVER)
01920                                         tcp_newstate(soc, TCP_STATE_LISTENING);
01921                                 else
01922                                         tcp_newstate(soc, TCP_STATE_CLOSED);
01923                                         
01924                                 return(-1);
01925                         }                       
01926                         
01927                         /* Is it ACK?                   */
01928                         
01929                         if( received_tcp_packet.hlen_flags & TCP_FLAG_ACK       ) {
01930                                 /* Rigth ACK?   */
01931                                 
01932                                 if( received_tcp_packet.ackno != soc->send_next ) {
01933                                         TCP_DEBUGOUT("ACK received but wrong Ack\n\r");
01934                                         return(-1);
01935                                 }
01936                                 
01937                                 TCP_DEBUGOUT("Our FIN is ACKed and peer wants to close too\r\n");
01938                                 TCP_DEBUGOUT("Next TIMED_WAIT\r\n");
01939 
01940                                 /* We have no unacked data      */
01941                                 
01942                                 soc->send_unacked = soc->send_next;
01943                                 
01944                                 tcp_newstate(soc, TCP_STATE_TIMED_WAIT);
01945                                 
01946                                 return(0);
01947                                                         
01948                         }
01949         
01950                         /* Is it repeated FIN?  */
01951                         
01952                         if( received_tcp_packet.hlen_flags & TCP_FLAG_FIN       ) {
01953                                 
01954                                 TCP_DEBUGOUT("Repeated FIN, repeat ACK\n\r");
01955                                 
01956                                 /* ACK FIN and all data */
01957                                 
01958                                 soc->receive_next = received_tcp_packet.seqno;
01959                                 soc->receive_next++;
01960                                 soc->receive_next += dlen;
01961                                 
01962                                 soc->myflags = TCP_FLAG_ACK;
01963                                 tcp_sendcontrol(sochandle);                     
01964                         
01965                                 return(0);
01966                         
01967                         }
01968 
01969                 
01970                         break;
01971                 
01972                 case TCP_STATE_LAST_ACK:
01973                 
01974                         TCP_DEBUGOUT("LAST_ACK State...\r\n");
01975                         
01976                         /* Check for RESET      */
01977                         
01978                         if(received_tcp_packet.hlen_flags & TCP_FLAG_RESET) {
01979                                 TCP_DEBUGOUT("ERROR:Reset received\r\n");
01980                                 
01981                                 /* Inform application   */
01982 
01983                                 soc->event_listener(sochandle, TCP_EVENT_ABORT, soc->rem_ip, soc->remport);                             
01984                                 
01985                                 if(soc->type & TCP_TYPE_SERVER)
01986                                         tcp_newstate(soc, TCP_STATE_LISTENING);
01987                                 else
01988                                         tcp_newstate(soc, TCP_STATE_CLOSED);
01989                                         
01990                                 return(-1);
01991                         }                       
01992                         
01993                         /* Is it ACK?   */
01994                         
01995                         if( received_tcp_packet.hlen_flags & TCP_FLAG_ACK       ) {
01996                                 /* Rigth ACK?   */
01997                                 
01998                                 if( received_tcp_packet.ackno != soc->send_next ) {
01999                                         TCP_DEBUGOUT("ACK received but wrong Ack\n\r");
02000                                         return(-1);
02001                                 }
02002                                 
02003                                 TCP_DEBUGOUT("Last ACK received, next LISTENING or CLOSED\r\n");
02004                                 
02005                                 /* We have no unacked data      */
02006                                 
02007                                 soc->send_unacked = soc->send_next;                             
02008                                 
02009                                 if(soc->type & TCP_TYPE_SERVER)
02010                                         tcp_newstate(soc, TCP_STATE_LISTENING);
02011                                 else
02012                                         tcp_newstate(soc, TCP_STATE_CLOSED);
02013                                                                                                 
02014                                 return(0);
02015                                                         
02016                         }                       
02017 
02018                         /* Is it repeated FIN?  */
02019                         
02020                         if( received_tcp_packet.hlen_flags & TCP_FLAG_FIN       ) {
02021                                 
02022                                 TCP_DEBUGOUT("Repeated FIN, repeat ACK\n\r");
02023                                 
02024                                 /* ACK FIN and all data */
02025                                 
02026                                 soc->receive_next = received_tcp_packet.seqno;
02027                                 soc->receive_next++;
02028                                 soc->receive_next += dlen;
02029                                         
02030                                 soc->myflags = TCP_FLAG_FIN | TCP_FLAG_ACK;
02031                                 tcp_sendcontrol(sochandle);
02032                                                         
02033                                 return(0);
02034                         
02035                         }                       
02036                         
02037                 
02038                         break;
02039                         
02040                 case TCP_STATE_TIMED_WAIT:
02041                 
02042                         TCP_DEBUGOUT("TIMED_WAIT State...\r\n");
02043                         
02044                         /* Check for RESET      */
02045                         
02046                         if(received_tcp_packet.hlen_flags & TCP_FLAG_RESET) {
02047                                 TCP_DEBUGOUT("ERROR:Reset received\r\n");
02048 
02049                                 /* Inform application   */
02050 
02051                                 soc->event_listener(sochandle, TCP_EVENT_ABORT, soc->rem_ip, soc->remport);                             
02052                                 
02053                                 if(soc->type & TCP_TYPE_SERVER)
02054                                         tcp_newstate(soc, TCP_STATE_LISTENING);
02055                                 else
02056                                         tcp_newstate(soc, TCP_STATE_CLOSED);
02057                                         
02058                                 return(-1);
02059                         }                       
02060                         
02061                         /* Is it repeated FIN?  */
02062                         
02063                         if( received_tcp_packet.hlen_flags & TCP_FLAG_FIN       ) {
02064                                 
02065                                 TCP_DEBUGOUT("Repeated FIN, repeat ACK\n\r");
02066                                 
02067                                 /* ACK FIN and all data */
02068                                 
02069                                 soc->receive_next = received_tcp_packet.seqno;
02070                                 soc->receive_next++;
02071                                 soc->receive_next += dlen;
02072                                         
02073                                 soc->myflags = TCP_FLAG_ACK;
02074                                 tcp_sendcontrol(sochandle);
02075                                                         
02076                                 return(0);
02077                         
02078                         }
02079                 
02080                         
02081                 
02082                         break;
02083         
02084         
02085                 default:
02086                 
02087                         TCP_DEBUGOUT("ERROR:TCP State machine in unknown state!!\r\n");
02088                         
02089                         tcp_sendreset(&received_tcp_packet, frame->sip);
02090                         
02091                         RESET_SYSTEM();
02092         
02093         }
02094         
02095         TCP_DEBUGOUT("Should not be there!\r\n");
02096         
02097         return(-1);
02098                 
02099 }
02100 
02101 
02119 INT16 process_tcp_out (INT8 sockethandle, UINT8* buf, UINT16 blen, UINT16 dlen)
02120 {
02121         struct tcb* soc;
02122         UINT16 cs;
02123         UINT8 cs_cnt;
02124         UINT16 i;
02125         UINT8* buf_start;
02126         
02127         TCP_DEBUGOUT("Entering to send TCP packet\r\n");
02128         
02129         if( sockethandle < 0 ) {
02130                 TCP_DEBUGOUT("ERROR:Socket Handle not valid (<0)\r\n");
02131                 return(-1);
02132         }
02133         
02134         if( sockethandle > NO_OF_TCPSOCKETS ) {
02135                 TCP_DEBUGOUT("ERROR:Socket Handle not valid (>NO_OF_TCPSOCKETS)\r\n");
02136                 return(-1);
02137         }
02138         
02139         if( (dlen + MIN_TCP_HLEN) > blen ) {
02140                 TCP_DEBUGOUT("ERROR:Transmit buffer too small for TCP header\r\n");
02141                 return(-1);
02142         } 
02143         
02144         soc = &tcp_socket[sockethandle];                                /* Get socket   */
02145         
02146         buf_start = buf;
02147         
02148         if( (dlen + MIN_TCP_HLEN) > soc->send_mtu ) {
02149                 TCP_DEBUGOUT("ERROR:Send MTU exceeded\r\n");
02150                 return(-1);
02151         }
02152         
02153         /* Assemble TCP header to buffer        */
02154         
02155         *buf++ = (UINT8)(soc->locport >> 8);
02156         *buf++ = (UINT8)soc->locport;
02157         *buf++ = (UINT8)(soc->remport >> 8);
02158         *buf++ = (UINT8)soc->remport;
02159         *buf++ = (UINT8)(soc->send_unacked >>24);
02160         *buf++ = (UINT8)(soc->send_unacked >>16);
02161         *buf++ = (UINT8)(soc->send_unacked >>8);
02162         *buf++ = (UINT8)(soc->send_unacked);
02163         *buf++ = (UINT8)(soc->receive_next >>24);
02164         *buf++ = (UINT8)(soc->receive_next >>16);
02165         *buf++ = (UINT8)(soc->receive_next >>8);
02166         *buf++ = (UINT8)(soc->receive_next);
02167         *buf =  MIN_TCP_HLEN >> 2;
02168         *buf <<= 4;
02169         buf++;
02170         *buf++ = soc->myflags;
02171         *buf++ = (UINT8)(TCP_DEF_MTU >> 8);
02172         *buf++ = (UINT8)TCP_DEF_MTU;
02173         *buf++ = 0;                                                             /* Checksum     */
02174         *buf++ = 0;
02175         *buf++ = 0;                                                             /* Urgent       */
02176         *buf++ = 0;
02177         
02178          
02179         /* Calculate checksum   */
02180         
02181         cs = 0;
02182         cs_cnt = 0;
02183         
02184         /* Do it firstly to IP pseudo header    */
02185         
02186         cs = ip_checksum(cs, (UINT8)(localmachine.localip >> 24), cs_cnt++);    
02187         cs = ip_checksum(cs, (UINT8)(localmachine.localip >> 16), cs_cnt++);
02188         cs = ip_checksum(cs, (UINT8)(localmachine.localip >> 8), cs_cnt++);
02189         cs = ip_checksum(cs, (UINT8)localmachine.localip, cs_cnt++);
02190         
02191         cs = ip_checksum(cs, (UINT8)(soc->rem_ip >> 24), cs_cnt++);     
02192         cs = ip_checksum(cs, (UINT8)(soc->rem_ip >> 16), cs_cnt++);
02193         cs = ip_checksum(cs, (UINT8)(soc->rem_ip >> 8), cs_cnt++);
02194         cs = ip_checksum(cs, (UINT8)soc->rem_ip, cs_cnt++);     
02195         
02196         cs = ip_checksum(cs, 0, cs_cnt++);
02197         
02198         cs = ip_checksum(cs, (UINT8)IP_TCP, cs_cnt++);
02199                 
02200         cs = ip_checksum(cs, (UINT8)((dlen + MIN_TCP_HLEN) >> 8), cs_cnt++);
02201         cs = ip_checksum(cs, (UINT8)(dlen + MIN_TCP_HLEN), cs_cnt++);
02202         
02203         /* Go to TCP header + data      */
02204         
02205         buf = buf_start;
02206         
02207         cs = ip_checksum_buf(cs, buf, dlen + MIN_TCP_HLEN);
02208                 
02209         cs = ~ cs;
02210 
02211 #if 0
02212         /* Is the padding required?     */
02213         
02214         if(dlen & 0x01) {
02215                 TCP_DEBUGOUT("Padding required\r\n");
02216                 *buf = 0;
02217                 dlen++;
02218         }
02219 #endif
02220         
02221         /* Save checksum in correct place       */
02222         
02223         buf = buf_start + 16;
02224         *buf++ = (UINT8)(cs >> 8);
02225         *buf = (UINT8)cs;
02226         
02227         /* Send it to IP        */
02228         
02229         TCP_DEBUGOUT("Sending TCP...\r\n");
02230         
02231         process_ip_out(soc->rem_ip, IP_TCP, soc->tos, 100, buf_start, dlen + MIN_TCP_HLEN);
02232         
02233         TCP_DEBUGOUT("TCP packet sent\r\n");
02234         
02235         return(0);
02236         
02237 
02238 }
02239 
02240 
02241 
02253 void tcp_sendcontrol (INT8 sockethandle)
02254 {
02255         UINT8 i;
02256 
02257         
02258         TCP_DEBUGOUT("Entering to send TCP control packet\r\n");
02259         
02260         kick_WD();
02261         
02262         if( sockethandle < 0 ) {
02263                 TCP_DEBUGOUT("ERROR:Socket Handle not valid (<0)\r\n");
02264                 return;
02265         }
02266         
02267         if( sockethandle > NO_OF_TCPSOCKETS ) {
02268                 TCP_DEBUGOUT("ERROR:Socket Handle not valid (>NO_OF_TCPSOCKETS)\r\n");
02269                 return;
02270         }
02271         
02272         process_tcp_out(sockethandle, &tcp_tempbuf[0], MIN_TCP_HLEN + 1, 0);
02273         
02274         return;
02275         
02276         
02277 }
02278 
02294 void tcp_sendreset (struct tcp_frame *frame, UINT32 remip)
02295 {
02296         struct tcb* soc;
02297 
02298         soc = &tcp_socket[NO_OF_TCPSOCKETS];                            /* Get socket   */
02299 
02300 
02301         /* Is this itself a reset packet?       */
02302         
02303         if( frame->hlen_flags & TCP_FLAG_RESET )
02304                 return;
02305 
02306         /* Set temporary tcb variables  */
02307         
02308         soc->rem_ip = remip;
02309         soc->remport = frame->sport;
02310         soc->locport = frame->dport;
02311         soc->tos = 0;
02312         
02313         /* Does the packet have ACK flag set?   */
02314         
02315         if( frame->hlen_flags & TCP_FLAG_ACK ) {
02316                 /* Jup, use it as our seq       */
02317                 
02318                 soc->send_unacked = frame->ackno;
02319                 soc->myflags = TCP_FLAG_RESET;  
02320                 soc->receive_next = frame->seqno;
02321         } else {
02322                 soc->send_unacked = 0;
02323                 soc->myflags = TCP_FLAG_RESET | TCP_FLAG_ACK;   
02324                 soc->receive_next = frame->seqno+1;
02325         }
02326                 
02327         
02328         soc->send_mtu = TCP_DEF_MTU;
02329         
02330         tcp_sendcontrol(NO_OF_TCPSOCKETS);
02331 
02332 }
02333 
02334 
02346 UINT32 tcp_initseq (void)
02347 {
02348 
02349         TCP_DEBUGOUT("Calculating initial sequence number\r\n");
02350         
02351         return( ( (UINT32)base_timer << 24) | 0x00FFFFFF );
02352 
02353 }
02354 
02369 INT8 tcp_mapsocket (struct ip_frame* ipframe, struct tcp_frame* tcpframe)
02370 {
02371         struct tcb* soc;
02372         UINT8 i;
02373 
02374         
02375         /* Check if there is already connection on      */
02376         
02377         for( i=0; i < NO_OF_TCPSOCKETS; i++) {
02378                 soc = &tcp_socket[i];                                   /* Get socket   */
02379                 
02380                 if(soc->state == TCP_STATE_LISTENING)
02381                         continue;                                                       /* No match             */
02382                 if(soc->remport != tcpframe->sport)
02383                         continue;                                               
02384                 if(soc->locport != tcpframe->dport)
02385                         continue;                                               
02386                 if(soc->rem_ip != ipframe->sip) 
02387                         continue;                                               
02388                 
02389                 /* There is connection on already       */
02390                 
02391                 TCP_DEBUGOUT("Active connection socket found\r\n");
02392                 
02393                 return(i);
02394         }
02395         
02396         /* Allocate listening one if SYN packet (Connection Request)    */
02397         
02398         TCP_DEBUGOUT("No active connection, checking if SYN packet\r\n");
02399         
02400         /* Is it SYN?   */
02401         
02402         if( (tcpframe->hlen_flags & TCP_FLAG_SYN) == 0 )
02403                 return(-1);
02404         if( tcpframe->hlen_flags & TCP_FLAG_ACK )
02405                 return(-1);
02406         if( tcpframe->hlen_flags & TCP_FLAG_RESET )
02407                 return(-1);
02408         if( tcpframe->hlen_flags & TCP_FLAG_FIN )
02409                 return(-1);
02410         
02411         TCP_DEBUGOUT("Trying to allocate listening one for SYN packet\r\n");
02412         
02413         /* Search listening sockets     */
02414         
02415         for( i=0; i < NO_OF_TCPSOCKETS; i++) {
02416                 soc = &tcp_socket[i];                           /* Get socket   */
02417         
02418                 if(soc->state != TCP_STATE_LISTENING)
02419                         continue;       
02420                 
02421                 if(soc->locport != tcpframe->dport)
02422                         continue;
02423                 
02424                 /* Bind it      */
02425                 
02426                 soc->rem_ip = ipframe->sip;
02427                 soc->remport = tcpframe->sport;
02428                 
02429                 TCP_DEBUGOUT("Allocated new socket\r\n");
02430                 
02431                 return(i);
02432                 
02433         }
02434         
02435         /* No success   */
02436         
02437         TCP_DEBUGOUT("ERROR:No socket found or allocated for TCP packet\r\n");
02438         
02439         return(-1);
02440 
02441 }
02442 
02443 
02455 void tcp_newstate (struct tcb* soc, UINT8 nstate)
02456 {
02457         soc->state = nstate;
02458         soc->retries_left = TCP_DEF_RETRIES;
02459 
02460         /* In some states we don't want to wait for many retries (e.g. TIMED_WAIT)      */
02461         
02462         switch(soc->state) {
02463                 case TCP_STATE_TIMED_WAIT:
02464                         soc->retries_left = 0;
02465                         break;
02466                 
02467                 case TCP_STATE_SYN_SENT:        
02468                         /* When we are sending SYN it's propably that ARP is not valid  */
02469                         /* Do retransmit faster on first time                                                   */
02470                         init_timer(soc->retransmit_timerh, TCP_INIT_RETRY_TOUT*TIMERTIC);
02471                         soc->retries_left = TCP_CON_ATTEMPTS;
02472                         break;
02473 
02474                 case TCP_STATE_LAST_ACK:
02475                 case TCP_STATE_FINW1:
02476                 case TCP_STATE_FINW2:
02477                 case TCP_STATE_CLOSING:
02478                         soc->retries_left = 1;
02479                         break;
02480                 
02481                 default:
02482                         break;
02483         
02484         }
02485         
02486         
02487         /* KeepAlive timer      */
02488         if(soc->state == TCP_STATE_CONNECTED)
02489                 init_timer(soc->persist_timerh, soc->tout);
02490         
02491         /* Retransmit timer     */
02492         
02493         init_timer(soc->retransmit_timerh, TCP_DEF_RETRY_TOUT*TIMERTIC);
02494         
02495         return;
02496 
02497 
02498 }
02499 
02511 UINT16 tcp_getfreeport (void)
02512 {
02513         struct tcb* soc;
02514         static UINT16 lastport = 1;
02515         UINT16 start;
02516         UINT16 i;
02517         
02518 
02519         /* Try with every port to every socket untill free found        */
02520                 
02521         for( start = lastport++; start != lastport; lastport++) {
02522                 if(lastport == TCP_PORTS_END)
02523                         lastport = 1;
02524                         
02525                 for(i = 0; i < NO_OF_TCPSOCKETS; i++) {
02526                         soc = &tcp_socket[i];                                   /* Get socket   */
02527                         
02528                         if( (soc->state > TCP_STATE_CLOSED) && (soc->locport == lastport) ) {
02529                                 /* Blaah, this socket has reserved the port, go to next one     */
02530                                 break; 
02531                         }
02532                         
02533                 }       
02534                         
02535                 /* Did we found it?     */
02536                         
02537                 if( i == NO_OF_TCPSOCKETS)
02538                         break; 
02539                         
02540         }
02541                 
02542         if(lastport == start) {
02543                 TCP_DEBUGOUT("Out of TCP ports!!\n\r");
02544                 return(0);
02545         }
02546                 
02547         return(lastport);
02548                 
02549 }
02550 
02551 
02552 
02567 UINT8 tcp_check_cs (struct ip_frame* ipframe, UINT16 len)
02568 {
02569         UINT16 cs;
02570         UINT8 cs_cnt;
02571         UINT16 i;
02572         
02573         cs = 0;
02574         cs_cnt = 0;
02575         
02576         /* Do it firstly to IP pseudo header    */
02577         
02578         cs = ip_checksum(cs, (UINT8)(ipframe->sip >> 24), cs_cnt++);    
02579         cs = ip_checksum(cs, (UINT8)(ipframe->sip >> 16), cs_cnt++);
02580         cs = ip_checksum(cs, (UINT8)(ipframe->sip >> 8), cs_cnt++);
02581         cs = ip_checksum(cs, (UINT8)ipframe->sip, cs_cnt++);
02582         
02583         cs = ip_checksum(cs, (UINT8)(ipframe->dip >> 24), cs_cnt++);    
02584         cs = ip_checksum(cs, (UINT8)(ipframe->dip >> 16), cs_cnt++);
02585         cs = ip_checksum(cs, (UINT8)(ipframe->dip >> 8), cs_cnt++);
02586         cs = ip_checksum(cs, (UINT8)ipframe->dip, cs_cnt++);    
02587         
02588         cs = ip_checksum(cs, 0, cs_cnt++);
02589         
02590         cs = ip_checksum(cs, (UINT8)ipframe->protocol, cs_cnt++);
02591                 
02592         cs = ip_checksum(cs, (UINT8)(len >> 8), cs_cnt++);
02593         cs = ip_checksum(cs, (UINT8)len, cs_cnt++);
02594         
02595         /* Go to TCP data       */
02596         while(len>15)
02597         {               
02598                 RECEIVE_NETWORK_BUF(tcp_tempbuf,16);    
02599                 
02600                 cs = ip_checksum_buf(cs, tcp_tempbuf,16);
02601                 len -= 16;      
02602                 cs_cnt += 16;
02603         }
02604         
02605         while(len--){
02606                 cs = ip_checksum(cs, RECEIVE_NETWORK_B(), cs_cnt++);
02607         }
02608         
02609         cs = ~ cs;
02610         
02611         if(cs != IP_GOOD_CS) {
02612                 return (0);
02613         }
02614         
02615         /* It's OK      */
02616         
02617         return(1);
02618         
02619 
02620 }
02621 

Generated on Sun Aug 3 20:33:00 2003 for OpenTCP by doxygen1.2.18