FreeRTOS_TCP_IP.c 181 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517251825192520252125222523252425252526252725282529253025312532253325342535253625372538253925402541254225432544254525462547254825492550255125522553255425552556255725582559256025612562256325642565256625672568256925702571257225732574257525762577257825792580258125822583258425852586258725882589259025912592259325942595259625972598259926002601260226032604260526062607260826092610261126122613261426152616261726182619262026212622262326242625262626272628262926302631263226332634263526362637263826392640264126422643264426452646264726482649265026512652265326542655265626572658265926602661266226632664266526662667266826692670267126722673267426752676267726782679268026812682268326842685268626872688268926902691269226932694269526962697269826992700270127022703270427052706270727082709271027112712271327142715271627172718271927202721272227232724272527262727272827292730273127322733273427352736273727382739274027412742274327442745274627472748274927502751275227532754275527562757275827592760276127622763276427652766276727682769277027712772277327742775277627772778277927802781278227832784278527862787278827892790279127922793279427952796279727982799280028012802280328042805280628072808280928102811281228132814281528162817281828192820282128222823282428252826282728282829283028312832283328342835283628372838283928402841284228432844284528462847284828492850285128522853285428552856285728582859286028612862286328642865286628672868286928702871287228732874287528762877287828792880288128822883288428852886288728882889289028912892289328942895289628972898289929002901290229032904290529062907290829092910291129122913291429152916291729182919292029212922292329242925292629272928292929302931293229332934293529362937293829392940294129422943294429452946294729482949295029512952295329542955295629572958295929602961296229632964296529662967296829692970297129722973297429752976297729782979298029812982298329842985298629872988298929902991299229932994299529962997299829993000300130023003300430053006300730083009301030113012301330143015301630173018301930203021302230233024302530263027302830293030303130323033303430353036303730383039304030413042304330443045304630473048304930503051305230533054305530563057305830593060306130623063306430653066306730683069307030713072307330743075307630773078307930803081308230833084308530863087308830893090309130923093309430953096309730983099310031013102310331043105310631073108310931103111311231133114311531163117311831193120312131223123312431253126312731283129313031313132313331343135313631373138313931403141314231433144314531463147314831493150315131523153315431553156315731583159316031613162316331643165316631673168316931703171317231733174317531763177317831793180318131823183318431853186318731883189319031913192319331943195319631973198319932003201320232033204320532063207320832093210321132123213321432153216321732183219322032213222322332243225322632273228322932303231323232333234323532363237323832393240324132423243324432453246324732483249325032513252325332543255325632573258325932603261326232633264326532663267326832693270327132723273327432753276327732783279328032813282328332843285328632873288328932903291329232933294329532963297329832993300330133023303330433053306330733083309331033113312331333143315331633173318331933203321332233233324332533263327332833293330333133323333333433353336333733383339334033413342334333443345334633473348334933503351335233533354335533563357335833593360336133623363336433653366336733683369337033713372337333743375337633773378337933803381338233833384338533863387338833893390339133923393339433953396339733983399340034013402340334043405340634073408340934103411341234133414341534163417341834193420342134223423342434253426342734283429343034313432343334343435343634373438343934403441344234433444344534463447344834493450345134523453345434553456345734583459346034613462346334643465346634673468346934703471347234733474347534763477347834793480348134823483348434853486348734883489349034913492349334943495349634973498349935003501350235033504350535063507350835093510351135123513351435153516351735183519352035213522352335243525352635273528352935303531353235333534353535363537353835393540354135423543354435453546354735483549355035513552355335543555355635573558355935603561356235633564356535663567356835693570357135723573357435753576357735783579358035813582358335843585358635873588358935903591359235933594359535963597359835993600360136023603360436053606360736083609361036113612361336143615361636173618361936203621362236233624362536263627362836293630363136323633363436353636363736383639364036413642364336443645364636473648364936503651365236533654365536563657365836593660366136623663366436653666366736683669367036713672367336743675367636773678367936803681368236833684368536863687368836893690369136923693369436953696369736983699370037013702370337043705370637073708370937103711371237133714371537163717371837193720372137223723372437253726372737283729373037313732373337343735373637373738373937403741374237433744374537463747374837493750375137523753375437553756375737583759376037613762376337643765376637673768376937703771377237733774377537763777377837793780378137823783378437853786378737883789379037913792379337943795379637973798379938003801380238033804380538063807380838093810381138123813381438153816381738183819382038213822382338243825382638273828382938303831383238333834383538363837383838393840384138423843384438453846384738483849385038513852385338543855385638573858385938603861386238633864386538663867386838693870387138723873387438753876387738783879388038813882388338843885388638873888388938903891389238933894389538963897389838993900390139023903390439053906390739083909391039113912391339143915391639173918391939203921392239233924392539263927392839293930393139323933393439353936393739383939394039413942394339443945394639473948394939503951395239533954395539563957395839593960396139623963396439653966396739683969397039713972397339743975397639773978397939803981
  1. /*
  2. * FreeRTOS+TCP V2.3.2 LTS Patch 1
  3. * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
  4. *
  5. * Permission is hereby granted, free of charge, to any person obtaining a copy of
  6. * this software and associated documentation files (the "Software"), to deal in
  7. * the Software without restriction, including without limitation the rights to
  8. * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
  9. * the Software, and to permit persons to whom the Software is furnished to do so,
  10. * subject to the following conditions:
  11. *
  12. * The above copyright notice and this permission notice shall be included in all
  13. * copies or substantial portions of the Software.
  14. *
  15. * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  16. * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
  17. * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
  18. * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
  19. * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
  20. * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  21. *
  22. * http://aws.amazon.com/freertos
  23. * http://www.FreeRTOS.org
  24. */
  25. /**
  26. * @file FreeRTOS_TCP_IP.c
  27. * @brief Module which handles the TCP connections for FreeRTOS+TCP.
  28. * It depends on FreeRTOS_TCP_WIN.c, which handles the TCP windowing
  29. * schemes.
  30. *
  31. * Endianness: in this module all ports and IP addresses are stored in
  32. * host byte-order, except fields in the IP-packets
  33. */
  34. /* Standard includes. */
  35. #include <stdint.h>
  36. #include <stdio.h>
  37. /* FreeRTOS includes. */
  38. #include "FreeRTOS.h"
  39. #include "task.h"
  40. #include "queue.h"
  41. #include "semphr.h"
  42. /* FreeRTOS+TCP includes. */
  43. #include "FreeRTOS_IP.h"
  44. #include "FreeRTOS_Sockets.h"
  45. #include "FreeRTOS_IP_Private.h"
  46. #include "FreeRTOS_UDP_IP.h"
  47. #include "FreeRTOS_DHCP.h"
  48. #include "NetworkInterface.h"
  49. #include "NetworkBufferManagement.h"
  50. #include "FreeRTOS_ARP.h"
  51. /* Just make sure the contents doesn't get compiled if TCP is not enabled. */
  52. #if ipconfigUSE_TCP == 1
  53. /*lint -e750 local macro not referenced [MISRA 2012 Rule 2.5, advisory] */
  54. /*
  55. * The meaning of the TCP flags:
  56. */
  57. #define tcpTCP_FLAG_FIN ( ( uint8_t ) 0x01U ) /**< No more data from sender. */
  58. #define tcpTCP_FLAG_SYN ( ( uint8_t ) 0x02U ) /**< Synchronize sequence numbers. */
  59. #define tcpTCP_FLAG_RST ( ( uint8_t ) 0x04U ) /**< Reset the connection. */
  60. #define tcpTCP_FLAG_PSH ( ( uint8_t ) 0x08U ) /**< Push function: please push buffered data to the recv application. */
  61. #define tcpTCP_FLAG_ACK ( ( uint8_t ) 0x10U ) /**< Acknowledgment field is significant. */
  62. #define tcpTCP_FLAG_URG ( ( uint8_t ) 0x20U ) /**< Urgent pointer field is significant. */
  63. #define tcpTCP_FLAG_ECN ( ( uint8_t ) 0x40U ) /**< ECN-Echo. */
  64. #define tcpTCP_FLAG_CWR ( ( uint8_t ) 0x80U ) /**< Congestion Window Reduced. */
  65. #define tcpTCP_FLAG_CTRL ( ( uint8_t ) 0x1FU ) /**< A mask to filter all protocol flags. */
  66. /*
  67. * A few values of the TCP options:
  68. */
  69. #define tcpTCP_OPT_END 0U /**< End of TCP options list. */
  70. #define tcpTCP_OPT_NOOP 1U /**< "No-operation" TCP option. */
  71. #define tcpTCP_OPT_MSS 2U /**< Maximum segment size TCP option. */
  72. #define tcpTCP_OPT_WSOPT 3U /**< TCP Window Scale Option (3-byte long). */
  73. #define tcpTCP_OPT_SACK_P 4U /**< Advertise that SACK is permitted. */
  74. #define tcpTCP_OPT_SACK_A 5U /**< SACK option with first/last. */
  75. #define tcpTCP_OPT_TIMESTAMP 8U /**< Time-stamp option. */
  76. #define tcpTCP_OPT_MSS_LEN 4U /**< Length of TCP MSS option. */
  77. #define tcpTCP_OPT_WSOPT_LEN 3U /**< Length of TCP WSOPT option. */
  78. #define tcpTCP_OPT_TIMESTAMP_LEN 10 /**< fixed length of the time-stamp option. */
  79. #ifndef ipconfigTCP_ACK_EARLIER_PACKET
  80. #define ipconfigTCP_ACK_EARLIER_PACKET 1 /**< Acknowledge an earlier packet. */
  81. #endif
  82. /** @brief
  83. * The macro tcpNOW_CONNECTED() is use to determine if the connection makes a
  84. * transition from connected to non-connected and vice versa.
  85. * tcpNOW_CONNECTED() returns true when the status has one of these values:
  86. * eESTABLISHED, eFIN_WAIT_1, eFIN_WAIT_2, eCLOSING, eLAST_ACK, eTIME_WAIT
  87. * Technically the connection status is closed earlier, but the library wants
  88. * to prevent that the socket will be deleted before the last ACK has been
  89. * and thus causing a 'RST' packet on either side.
  90. */
  91. #define tcpNOW_CONNECTED( status ) \
  92. ( ( ( ( status ) >= ( BaseType_t ) eESTABLISHED ) && ( ( status ) != ( BaseType_t ) eCLOSE_WAIT ) ) ? 1 : 0 )
  93. /** @brief
  94. * The highest 4 bits in the TCP offset byte indicate the total length of the
  95. * TCP header, divided by 4.
  96. */
  97. #define tcpVALID_BITS_IN_TCP_OFFSET_BYTE ( 0xF0U )
  98. /*
  99. * Acknowledgements to TCP data packets may be delayed as long as more is being expected.
  100. * A normal delay would be 200ms. Here a much shorter delay of 20 ms is being used to
  101. * gain performance.
  102. */
  103. #define tcpDELAYED_ACK_SHORT_DELAY_MS ( 2 ) /**< Should not become smaller than 1. */
  104. #define tcpDELAYED_ACK_LONGER_DELAY_MS ( 20 ) /**< Longer delay for ACK. */
  105. /** @brief
  106. * The MSS (Maximum Segment Size) will be taken as large as possible. However, packets with
  107. * an MSS of 1460 bytes won't be transported through the internet. The MSS will be reduced
  108. * to 1400 bytes.
  109. */
  110. #define tcpREDUCED_MSS_THROUGH_INTERNET ( 1400 )
  111. /** @brief
  112. * When there are no TCP options, the TCP offset equals 20 bytes, which is stored as
  113. * the number 5 (words) in the higher nibble of the TCP-offset byte.
  114. */
  115. #define tcpTCP_OFFSET_LENGTH_BITS ( 0xf0U )
  116. #define tcpTCP_OFFSET_STANDARD_LENGTH ( 0x50U ) /**< Standard TCP packet offset. */
  117. /** @brief
  118. * Each TCP socket is checked regularly to see if it can send data packets.
  119. * By default, the maximum number of packets sent during one check is limited to 8.
  120. * This amount may be further limited by setting the socket's TX window size.
  121. */
  122. #if ( !defined( SEND_REPEATED_COUNT ) )
  123. #define SEND_REPEATED_COUNT ( 8 )
  124. #endif /* !defined( SEND_REPEATED_COUNT ) */
  125. /** @brief
  126. * Define a maximum period of time (ms) to leave a TCP-socket unattended.
  127. * When a TCP timer expires, retries and keep-alive messages will be checked.
  128. */
  129. #ifndef tcpMAXIMUM_TCP_WAKEUP_TIME_MS
  130. #define tcpMAXIMUM_TCP_WAKEUP_TIME_MS 20000U
  131. #endif
  132. /* Two macro's that were introduced to work with both IPv4 and IPv6. */
  133. #define xIPHeaderSize( pxNetworkBuffer ) ( ipSIZE_OF_IPv4_HEADER ) /**< Size of IP Header. */
  134. #define uxIPHeaderSizeSocket( pxSocket ) ( ipSIZE_OF_IPv4_HEADER ) /**< Size of IP Header socket. */
  135. /*
  136. * Returns true if the socket must be checked. Non-active sockets are waiting
  137. * for user action, either connect() or close().
  138. */
  139. static BaseType_t prvTCPSocketIsActive( eIPTCPState_t xStatus );
  140. /*
  141. * Either sends a SYN or calls prvTCPSendRepeated (for regular messages).
  142. */
  143. static int32_t prvTCPSendPacket( FreeRTOS_Socket_t * pxSocket );
  144. /*
  145. * Try to send a series of messages.
  146. */
  147. static int32_t prvTCPSendRepeated( FreeRTOS_Socket_t * pxSocket,
  148. NetworkBufferDescriptor_t ** ppxNetworkBuffer );
  149. /*
  150. * Return or send a packet to the other party.
  151. */
  152. static void prvTCPReturnPacket( FreeRTOS_Socket_t * pxSocket,
  153. NetworkBufferDescriptor_t * pxDescriptor,
  154. uint32_t ulLen,
  155. BaseType_t xReleaseAfterSend );
  156. /*
  157. * Initialise the data structures which keep track of the TCP windowing system.
  158. */
  159. static void prvTCPCreateWindow( FreeRTOS_Socket_t * pxSocket );
  160. /*
  161. * Let ARP look-up the MAC-address of the peer and initialise the first SYN
  162. * packet.
  163. */
  164. static BaseType_t prvTCPPrepareConnect( FreeRTOS_Socket_t * pxSocket );
  165. #if ( ipconfigHAS_DEBUG_PRINTF != 0 )
  166. /*
  167. * For logging and debugging: make a string showing the TCP flags.
  168. */
  169. static const char * prvTCPFlagMeaning( UBaseType_t xFlags );
  170. #endif /* ipconfigHAS_DEBUG_PRINTF != 0 */
  171. /*
  172. * Parse the TCP option(s) received, if present.
  173. */
  174. _static void prvCheckOptions( FreeRTOS_Socket_t * pxSocket,
  175. const NetworkBufferDescriptor_t * pxNetworkBuffer );
  176. /*
  177. * Identify and deal with a single TCP header option, advancing the pointer to
  178. * the header. This function returns pdTRUE or pdFALSE depending on whether the
  179. * caller should continue to parse more header options or break the loop.
  180. */
  181. _static size_t prvSingleStepTCPHeaderOptions( const uint8_t * const pucPtr,
  182. size_t uxTotalLength,
  183. FreeRTOS_Socket_t * const pxSocket,
  184. BaseType_t xHasSYNFlag );
  185. #if ( ipconfigUSE_TCP_WIN == 1 )
  186. /*
  187. * Skip past TCP header options when doing Selective ACK, until there are no
  188. * more options left.
  189. */
  190. _static void prvReadSackOption( const uint8_t * const pucPtr,
  191. size_t uxIndex,
  192. FreeRTOS_Socket_t * const pxSocket );
  193. #endif /* ( ipconfigUSE_TCP_WIN == 1 ) */
  194. /*
  195. * Set the initial properties in the options fields, like the preferred
  196. * value of MSS and whether SACK allowed. Will be transmitted in the state
  197. * 'eCONNECT_SYN'.
  198. */
  199. static UBaseType_t prvSetSynAckOptions( FreeRTOS_Socket_t * pxSocket,
  200. TCPHeader_t * pxTCPHeader );
  201. /*
  202. * For anti-hang protection and TCP keep-alive messages. Called in two places:
  203. * after receiving a packet and after a state change. The socket's alive timer
  204. * may be reset.
  205. */
  206. static void prvTCPTouchSocket( FreeRTOS_Socket_t * pxSocket );
  207. /*
  208. * Prepare an outgoing message, if anything has to be sent.
  209. */
  210. static int32_t prvTCPPrepareSend( FreeRTOS_Socket_t * pxSocket,
  211. NetworkBufferDescriptor_t ** ppxNetworkBuffer,
  212. UBaseType_t uxOptionsLength );
  213. /*
  214. * Calculate when this socket needs to be checked to do (re-)transmissions.
  215. */
  216. static TickType_t prvTCPNextTimeout( FreeRTOS_Socket_t * pxSocket );
  217. /*
  218. * The API FreeRTOS_send() adds data to the TX stream. Add
  219. * this data to the windowing system to it can be transmitted.
  220. */
  221. static void prvTCPAddTxData( FreeRTOS_Socket_t * pxSocket );
  222. /*
  223. * Called to handle the closure of a TCP connection.
  224. */
  225. static BaseType_t prvTCPHandleFin( FreeRTOS_Socket_t * pxSocket,
  226. const NetworkBufferDescriptor_t * pxNetworkBuffer );
  227. /*
  228. * Called from prvTCPHandleState(). Find the TCP payload data and check and
  229. * return its length.
  230. */
  231. static BaseType_t prvCheckRxData( const NetworkBufferDescriptor_t * pxNetworkBuffer,
  232. uint8_t ** ppucRecvData );
  233. /*
  234. * Called from prvTCPHandleState(). Check if the payload data may be accepted.
  235. * If so, it will be added to the socket's reception queue.
  236. */
  237. static BaseType_t prvStoreRxData( FreeRTOS_Socket_t * pxSocket,
  238. const uint8_t * pucRecvData,
  239. NetworkBufferDescriptor_t * pxNetworkBuffer,
  240. uint32_t ulReceiveLength );
  241. /*
  242. * Set the TCP options (if any) for the outgoing packet.
  243. */
  244. static UBaseType_t prvSetOptions( FreeRTOS_Socket_t * pxSocket,
  245. const NetworkBufferDescriptor_t * pxNetworkBuffer );
  246. /*
  247. * Called from prvTCPHandleState() as long as the TCP status is eSYN_RECEIVED to
  248. * eCONNECT_SYN.
  249. */
  250. static BaseType_t prvHandleSynReceived( FreeRTOS_Socket_t * pxSocket,
  251. const NetworkBufferDescriptor_t * pxNetworkBuffer,
  252. uint32_t ulReceiveLength,
  253. UBaseType_t uxOptionsLength );
  254. /*
  255. * Called from prvTCPHandleState() as long as the TCP status is eESTABLISHED.
  256. */
  257. static BaseType_t prvHandleEstablished( FreeRTOS_Socket_t * pxSocket,
  258. NetworkBufferDescriptor_t ** ppxNetworkBuffer,
  259. uint32_t ulReceiveLength,
  260. UBaseType_t uxOptionsLength );
  261. /*
  262. * Called from prvTCPHandleState(). There is data to be sent.
  263. * If ipconfigUSE_TCP_WIN is defined, and if only an ACK must be sent, it will
  264. * be checked if it would better be postponed for efficiency.
  265. */
  266. static BaseType_t prvSendData( FreeRTOS_Socket_t * pxSocket,
  267. NetworkBufferDescriptor_t ** ppxNetworkBuffer,
  268. uint32_t ulReceiveLength,
  269. BaseType_t xByteCount );
  270. /*
  271. * The heart of all: check incoming packet for valid data and acks and do what
  272. * is necessary in each state.
  273. */
  274. static BaseType_t prvTCPHandleState( FreeRTOS_Socket_t * pxSocket,
  275. NetworkBufferDescriptor_t ** ppxNetworkBuffer );
  276. /*
  277. * Common code for sending a TCP protocol control packet (i.e. no options, no
  278. * payload, just flags).
  279. */
  280. static BaseType_t prvTCPSendSpecialPacketHelper( NetworkBufferDescriptor_t * pxNetworkBuffer,
  281. uint8_t ucTCPFlags );
  282. /*
  283. * A "challenge ACK" is as per https://tools.ietf.org/html/rfc5961#section-3.2,
  284. * case #3. In summary, an RST was received with a sequence number that is
  285. * unexpected but still within the window.
  286. */
  287. static BaseType_t prvTCPSendChallengeAck( NetworkBufferDescriptor_t * pxNetworkBuffer );
  288. /*
  289. * Reply to a peer with the RST flag on, in case a packet can not be handled.
  290. */
  291. static BaseType_t prvTCPSendReset( NetworkBufferDescriptor_t * pxNetworkBuffer );
  292. /*
  293. * Set the initial value for MSS (Maximum Segment Size) to be used.
  294. */
  295. static void prvSocketSetMSS( FreeRTOS_Socket_t * pxSocket );
  296. /*
  297. * Return either a newly created socket, or the current socket in a connected
  298. * state (depends on the 'bReuseSocket' flag).
  299. */
  300. static FreeRTOS_Socket_t * prvHandleListen( FreeRTOS_Socket_t * pxSocket,
  301. NetworkBufferDescriptor_t * pxNetworkBuffer );
  302. /*
  303. * After a listening socket receives a new connection, it may duplicate itself.
  304. * The copying takes place in prvTCPSocketCopy.
  305. */
  306. static BaseType_t prvTCPSocketCopy( FreeRTOS_Socket_t * pxNewSocket,
  307. FreeRTOS_Socket_t * pxSocket );
  308. /*
  309. * prvTCPStatusAgeCheck() will see if the socket has been in a non-connected
  310. * state for too long. If so, the socket will be closed, and -1 will be
  311. * returned.
  312. */
  313. #if ( ipconfigTCP_HANG_PROTECTION == 1 )
  314. static BaseType_t prvTCPStatusAgeCheck( FreeRTOS_Socket_t * pxSocket );
  315. #endif
  316. static NetworkBufferDescriptor_t * prvTCPBufferResize( const FreeRTOS_Socket_t * pxSocket,
  317. NetworkBufferDescriptor_t * pxNetworkBuffer,
  318. int32_t lDataLen,
  319. UBaseType_t uxOptionsLength );
  320. #if ( ipconfigUSE_TCP_WIN != 0 )
  321. static uint8_t prvWinScaleFactor( const FreeRTOS_Socket_t * pxSocket );
  322. #endif
  323. /*-----------------------------------------------------------*/
  324. /**
  325. * @brief Check whether the socket is active or not.
  326. *
  327. * @param[in] xStatus: The status of the socket.
  328. *
  329. * @return pdTRUE if the socket must be checked. Non-active sockets
  330. * are waiting for user action, either connect() or close().
  331. */
  332. static BaseType_t prvTCPSocketIsActive( eIPTCPState_t xStatus )
  333. {
  334. BaseType_t xResult;
  335. switch( xStatus )
  336. {
  337. case eCLOSED:
  338. case eCLOSE_WAIT:
  339. case eFIN_WAIT_2:
  340. case eCLOSING:
  341. case eTIME_WAIT:
  342. xResult = pdFALSE;
  343. break;
  344. case eTCP_LISTEN:
  345. case eCONNECT_SYN:
  346. case eSYN_FIRST:
  347. case eSYN_RECEIVED:
  348. case eESTABLISHED:
  349. case eFIN_WAIT_1:
  350. case eLAST_ACK:
  351. default:
  352. xResult = pdTRUE;
  353. break;
  354. }
  355. return xResult;
  356. }
  357. /*-----------------------------------------------------------*/
  358. #if ( ipconfigTCP_HANG_PROTECTION == 1 )
  359. /**
  360. * @brief Some of the TCP states may only last a certain amount of time.
  361. * This function checks if the socket is 'hanging', i.e. staying
  362. * too long in the same state.
  363. *
  364. * @param[in] The socket to be checked.
  365. *
  366. * @return pdFALSE if no checks are needed, pdTRUE if checks were done, or negative
  367. * in case the socket has reached a critical time-out. The socket will go to
  368. * the eCLOSE_WAIT state.
  369. */
  370. static BaseType_t prvTCPStatusAgeCheck( FreeRTOS_Socket_t * pxSocket )
  371. {
  372. BaseType_t xResult;
  373. eIPTCPState_t eState = ipNUMERIC_CAST( eIPTCPState_t, pxSocket->u.xTCP.ucTCPState );
  374. switch( eState )
  375. {
  376. case eESTABLISHED:
  377. /* If the 'ipconfigTCP_KEEP_ALIVE' option is enabled, sockets in
  378. * state ESTABLISHED can be protected using keep-alive messages. */
  379. xResult = pdFALSE;
  380. break;
  381. case eCLOSED:
  382. case eTCP_LISTEN:
  383. case eCLOSE_WAIT:
  384. /* These 3 states may last for ever, up to the owner. */
  385. xResult = pdFALSE;
  386. break;
  387. case eCONNECT_SYN:
  388. case eSYN_FIRST:
  389. case eSYN_RECEIVED:
  390. case eFIN_WAIT_1:
  391. case eFIN_WAIT_2:
  392. case eCLOSING:
  393. case eLAST_ACK:
  394. case eTIME_WAIT:
  395. default:
  396. /* All other (non-connected) states will get anti-hanging
  397. * protection. */
  398. xResult = pdTRUE;
  399. break;
  400. }
  401. if( xResult != pdFALSE )
  402. {
  403. /* How much time has past since the last active moment which is
  404. * defined as A) a state change or B) a packet has arrived. */
  405. TickType_t xAge = xTaskGetTickCount() - pxSocket->u.xTCP.xLastActTime;
  406. /* ipconfigTCP_HANG_PROTECTION_TIME is in units of seconds. */
  407. if( xAge > ( ( TickType_t ) ipconfigTCP_HANG_PROTECTION_TIME * ( TickType_t ) configTICK_RATE_HZ ) )
  408. {
  409. #if ( ipconfigHAS_DEBUG_PRINTF == 1 )
  410. {
  411. FreeRTOS_debug_printf( ( "Inactive socket closed: port %u rem %lxip:%u status %s\n",
  412. pxSocket->usLocalPort,
  413. pxSocket->u.xTCP.ulRemoteIP,
  414. pxSocket->u.xTCP.usRemotePort,
  415. FreeRTOS_GetTCPStateName( ( UBaseType_t ) pxSocket->u.xTCP.ucTCPState ) ) );
  416. }
  417. #endif /* ipconfigHAS_DEBUG_PRINTF */
  418. /* Move to eCLOSE_WAIT, user may close the socket. */
  419. vTCPStateChange( pxSocket, eCLOSE_WAIT );
  420. /* When 'bPassQueued' true, this socket is an orphan until it
  421. * gets connected. */
  422. if( pxSocket->u.xTCP.bits.bPassQueued != pdFALSE_UNSIGNED )
  423. {
  424. /* vTCPStateChange() has called FreeRTOS_closesocket()
  425. * in case the socket is not yet owned by the application.
  426. * Return a negative value to inform the caller that
  427. * the socket will be closed in the next cycle. */
  428. xResult = -1;
  429. }
  430. }
  431. }
  432. return xResult;
  433. }
  434. /*-----------------------------------------------------------*/
  435. #endif /* if ( ipconfigTCP_HANG_PROTECTION == 1 ) */
  436. /**
  437. * @brief As soon as a TCP socket timer expires, this function will be called
  438. * (from xTCPTimerCheck). It can send a delayed ACK or new data.
  439. *
  440. * @param[in] pxSocket: socket to be checked.
  441. *
  442. * @return 0 on success, a negative error code on failure. A negative value will be
  443. * returned in case the hang-protection has put the socket in a wait-close state.
  444. *
  445. * @note Sequence of calling (normally) :
  446. * IP-Task:
  447. * xTCPTimerCheck() // Check all sockets ( declared in FreeRTOS_Sockets.c )
  448. * xTCPSocketCheck() // Either send a delayed ACK or call prvTCPSendPacket()
  449. * prvTCPSendPacket() // Either send a SYN or call prvTCPSendRepeated ( regular messages )
  450. * prvTCPSendRepeated() // Send at most 8 messages on a row
  451. * prvTCPReturnPacket() // Prepare for returning
  452. * xNetworkInterfaceOutput() // Sends data to the NIC ( declared in portable/NetworkInterface/xxx )
  453. */
  454. BaseType_t xTCPSocketCheck( FreeRTOS_Socket_t * pxSocket )
  455. {
  456. BaseType_t xResult = 0;
  457. BaseType_t xReady = pdFALSE;
  458. if( ( pxSocket->u.xTCP.ucTCPState >= ( uint8_t ) eESTABLISHED ) && ( pxSocket->u.xTCP.txStream != NULL ) )
  459. {
  460. /* The API FreeRTOS_send() might have added data to the TX stream. Add
  461. * this data to the windowing system so it can be transmitted. */
  462. prvTCPAddTxData( pxSocket );
  463. }
  464. #if ( ipconfigUSE_TCP_WIN == 1 )
  465. {
  466. if( pxSocket->u.xTCP.pxAckMessage != NULL )
  467. {
  468. /* The first task of this regular socket check is to send-out delayed
  469. * ACK's. */
  470. if( pxSocket->u.xTCP.bits.bUserShutdown == pdFALSE_UNSIGNED )
  471. {
  472. /* Earlier data was received but not yet acknowledged. This
  473. * function is called when the TCP timer for the socket expires, the
  474. * ACK may be sent now. */
  475. if( pxSocket->u.xTCP.ucTCPState != ( uint8_t ) eCLOSED )
  476. {
  477. if( ( xTCPWindowLoggingLevel > 1 ) && ipconfigTCP_MAY_LOG_PORT( pxSocket->usLocalPort ) )
  478. {
  479. FreeRTOS_debug_printf( ( "Send[%u->%u] del ACK %lu SEQ %lu (len %u)\n",
  480. pxSocket->usLocalPort,
  481. pxSocket->u.xTCP.usRemotePort,
  482. pxSocket->u.xTCP.xTCPWindow.rx.ulCurrentSequenceNumber - pxSocket->u.xTCP.xTCPWindow.rx.ulFirstSequenceNumber,
  483. pxSocket->u.xTCP.xTCPWindow.ulOurSequenceNumber - pxSocket->u.xTCP.xTCPWindow.tx.ulFirstSequenceNumber,
  484. ( unsigned ) ipSIZE_OF_IPv4_HEADER + ipSIZE_OF_TCP_HEADER ) );
  485. }
  486. prvTCPReturnPacket( pxSocket, pxSocket->u.xTCP.pxAckMessage, ipSIZE_OF_IPv4_HEADER + ipSIZE_OF_TCP_HEADER, ipconfigZERO_COPY_TX_DRIVER );
  487. #if ( ipconfigZERO_COPY_TX_DRIVER != 0 )
  488. {
  489. /* The ownership has been passed to the SEND routine,
  490. * clear the pointer to it. */
  491. pxSocket->u.xTCP.pxAckMessage = NULL;
  492. }
  493. #endif /* ipconfigZERO_COPY_TX_DRIVER */
  494. }
  495. if( prvTCPNextTimeout( pxSocket ) > 1U )
  496. {
  497. /* Tell the code below that this function is ready. */
  498. xReady = pdTRUE;
  499. }
  500. }
  501. else
  502. {
  503. /* The user wants to perform an active shutdown(), skip sending
  504. * the delayed ACK. The function prvTCPSendPacket() will send the
  505. * FIN along with the ACK's. */
  506. }
  507. if( pxSocket->u.xTCP.pxAckMessage != NULL )
  508. {
  509. vReleaseNetworkBufferAndDescriptor( pxSocket->u.xTCP.pxAckMessage );
  510. pxSocket->u.xTCP.pxAckMessage = NULL;
  511. }
  512. }
  513. }
  514. #endif /* ipconfigUSE_TCP_WIN */
  515. if( xReady == pdFALSE )
  516. {
  517. /* The second task of this regular socket check is sending out data. */
  518. if( ( pxSocket->u.xTCP.ucTCPState >= ( uint8_t ) eESTABLISHED ) ||
  519. ( pxSocket->u.xTCP.ucTCPState == ( uint8_t ) eCONNECT_SYN ) )
  520. {
  521. ( void ) prvTCPSendPacket( pxSocket );
  522. }
  523. /* Set the time-out for the next wakeup for this socket. */
  524. ( void ) prvTCPNextTimeout( pxSocket );
  525. #if ( ipconfigTCP_HANG_PROTECTION == 1 )
  526. {
  527. /* In all (non-connected) states in which keep-alive messages can not be sent
  528. * the anti-hang protocol will close sockets that are 'hanging'. */
  529. xResult = prvTCPStatusAgeCheck( pxSocket );
  530. }
  531. #endif
  532. }
  533. return xResult;
  534. }
  535. /*-----------------------------------------------------------*/
  536. /**
  537. * @brief prvTCPSendPacket() will be called when the socket time-out has been reached.
  538. *
  539. * @param[in] pxSocket: The socket owning the connection.
  540. *
  541. * @return Number of bytes to be sent.
  542. *
  543. * @note It is only called by xTCPSocketCheck().
  544. */
  545. static int32_t prvTCPSendPacket( FreeRTOS_Socket_t * pxSocket )
  546. {
  547. int32_t lResult = 0;
  548. UBaseType_t uxOptionsLength, uxIntermediateResult = 0;
  549. NetworkBufferDescriptor_t * pxNetworkBuffer;
  550. if( pxSocket->u.xTCP.ucTCPState != ( uint8_t ) eCONNECT_SYN )
  551. {
  552. /* The connection is in a state other than SYN. */
  553. pxNetworkBuffer = NULL;
  554. /* prvTCPSendRepeated() will only create a network buffer if necessary,
  555. * i.e. when data must be sent to the peer. */
  556. lResult = prvTCPSendRepeated( pxSocket, &pxNetworkBuffer );
  557. if( pxNetworkBuffer != NULL )
  558. {
  559. vReleaseNetworkBufferAndDescriptor( pxNetworkBuffer );
  560. }
  561. }
  562. else
  563. {
  564. if( pxSocket->u.xTCP.ucRepCount >= 3U )
  565. {
  566. /* The connection is in the SYN status. The packet will be repeated
  567. * to most 3 times. When there is no response, the socket get the
  568. * status 'eCLOSE_WAIT'. */
  569. FreeRTOS_debug_printf( ( "Connect: giving up %lxip:%u\n",
  570. pxSocket->u.xTCP.ulRemoteIP, /* IP address of remote machine. */
  571. pxSocket->u.xTCP.usRemotePort ) ); /* Port on remote machine. */
  572. vTCPStateChange( pxSocket, eCLOSE_WAIT );
  573. }
  574. else if( ( pxSocket->u.xTCP.bits.bConnPrepared != pdFALSE_UNSIGNED ) || ( prvTCPPrepareConnect( pxSocket ) == pdTRUE ) )
  575. {
  576. ProtocolHeaders_t * pxProtocolHeaders;
  577. const UBaseType_t uxHeaderSize = ipSIZE_OF_IPv4_HEADER;
  578. /* Or else, if the connection has been prepared, or can be prepared
  579. * now, proceed to send the packet with the SYN flag.
  580. * prvTCPPrepareConnect() prepares 'xPacket' and returns pdTRUE if
  581. * the Ethernet address of the peer or the gateway is found. */
  582. pxProtocolHeaders = ipCAST_PTR_TO_TYPE_PTR( ProtocolHeaders_t, &( pxSocket->u.xTCP.xPacket.u.ucLastPacket[ ipSIZE_OF_ETH_HEADER + uxHeaderSize ] ) );
  583. /* About to send a SYN packet. Call prvSetSynAckOptions() to set
  584. * the proper options: The size of MSS and whether SACK's are
  585. * allowed. */
  586. uxOptionsLength = prvSetSynAckOptions( pxSocket, &( pxProtocolHeaders->xTCPHeader ) );
  587. /* Return the number of bytes to be sent. */
  588. uxIntermediateResult = uxIPHeaderSizeSocket( pxSocket ) + ipSIZE_OF_TCP_HEADER + uxOptionsLength;
  589. lResult = ( int32_t ) uxIntermediateResult;
  590. /* Set the TCP offset field: ipSIZE_OF_TCP_HEADER equals 20 and
  591. * uxOptionsLength is always a multiple of 4. The complete expression
  592. * would be:
  593. * ucTCPOffset = ( ( ipSIZE_OF_TCP_HEADER + uxOptionsLength ) / 4 ) << 4 */
  594. pxProtocolHeaders->xTCPHeader.ucTCPOffset = ( uint8_t ) ( ( ipSIZE_OF_TCP_HEADER + uxOptionsLength ) << 2 );
  595. /* Repeat Count is used for a connecting socket, to limit the number
  596. * of tries. */
  597. pxSocket->u.xTCP.ucRepCount++;
  598. /* Send the SYN message to make a connection. The messages is
  599. * stored in the socket field 'xPacket'. It will be wrapped in a
  600. * pseudo network buffer descriptor before it will be sent. */
  601. prvTCPReturnPacket( pxSocket, NULL, ( uint32_t ) lResult, pdFALSE );
  602. }
  603. else
  604. {
  605. /* Nothing to do. */
  606. }
  607. }
  608. /* Return the total number of bytes sent. */
  609. return lResult;
  610. }
  611. /*-----------------------------------------------------------*/
  612. /**
  613. * @brief prvTCPSendRepeated will try to send a series of messages, as
  614. * long as there is data to be sent and as long as the transmit
  615. * window isn't full.
  616. *
  617. * @param[in] pxSocket: The socket owning the connection.
  618. * @param[in,out] ppxNetworkBuffer: Pointer to pointer to the network buffer.
  619. *
  620. * @return Total number of bytes sent.
  621. */
  622. static int32_t prvTCPSendRepeated( FreeRTOS_Socket_t * pxSocket,
  623. NetworkBufferDescriptor_t ** ppxNetworkBuffer )
  624. {
  625. UBaseType_t uxIndex;
  626. int32_t lResult = 0;
  627. UBaseType_t uxOptionsLength = 0U;
  628. int32_t xSendLength;
  629. for( uxIndex = 0U; uxIndex < ( UBaseType_t ) SEND_REPEATED_COUNT; uxIndex++ )
  630. {
  631. /* prvTCPPrepareSend() might allocate a network buffer if there is data
  632. * to be sent. */
  633. xSendLength = prvTCPPrepareSend( pxSocket, ppxNetworkBuffer, uxOptionsLength );
  634. if( xSendLength <= 0 )
  635. {
  636. break;
  637. }
  638. /* And return the packet to the peer. */
  639. prvTCPReturnPacket( pxSocket, *ppxNetworkBuffer, ( uint32_t ) xSendLength, ipconfigZERO_COPY_TX_DRIVER );
  640. #if ( ipconfigZERO_COPY_TX_DRIVER != 0 )
  641. {
  642. *ppxNetworkBuffer = NULL;
  643. }
  644. #endif /* ipconfigZERO_COPY_TX_DRIVER */
  645. lResult += xSendLength;
  646. }
  647. /* Return the total number of bytes sent. */
  648. return lResult;
  649. }
  650. /*-----------------------------------------------------------*/
  651. /**
  652. * @brief Return (or send) a packet to the peer. The data is stored in pxBuffer,
  653. * which may either point to a real network buffer or to a TCP socket field
  654. * called 'xTCP.xPacket'. A temporary xNetworkBuffer will be used to pass
  655. * the data to the NIC.
  656. *
  657. * @param[in] pxSocket: The socket owning the connection.
  658. * @param[in] pxDescriptor: The network buffer descriptor carrying the packet.
  659. * @param[in] ulLen: Length of the packet being sent.
  660. * @param[in] xReleaseAfterSend: pdTRUE if the ownership of the descriptor is
  661. * transferred to the network interface.
  662. */
  663. static void prvTCPReturnPacket( FreeRTOS_Socket_t * pxSocket,
  664. NetworkBufferDescriptor_t * pxDescriptor,
  665. uint32_t ulLen,
  666. BaseType_t xReleaseAfterSend )
  667. {
  668. TCPPacket_t * pxTCPPacket;
  669. IPHeader_t * pxIPHeader;
  670. BaseType_t xDoRelease = xReleaseAfterSend;
  671. EthernetHeader_t * pxEthernetHeader;
  672. uint32_t ulFrontSpace, ulSpace, ulSourceAddress, ulWinSize;
  673. const TCPWindow_t * pxTCPWindow;
  674. NetworkBufferDescriptor_t * pxNetworkBuffer = pxDescriptor;
  675. NetworkBufferDescriptor_t xTempBuffer;
  676. /* memcpy() helper variables for MISRA Rule 21.15 compliance*/
  677. const void * pvCopySource;
  678. void * pvCopyDest;
  679. /* For sending, a pseudo network buffer will be used, as explained above. */
  680. if( pxNetworkBuffer == NULL )
  681. {
  682. pxNetworkBuffer = &xTempBuffer;
  683. #if ( ipconfigUSE_LINKED_RX_MESSAGES != 0 )
  684. {
  685. pxNetworkBuffer->pxNextBuffer = NULL;
  686. }
  687. #endif
  688. pxNetworkBuffer->pucEthernetBuffer = pxSocket->u.xTCP.xPacket.u.ucLastPacket;
  689. pxNetworkBuffer->xDataLength = sizeof( pxSocket->u.xTCP.xPacket.u.ucLastPacket );
  690. xDoRelease = pdFALSE;
  691. }
  692. #if ( ipconfigZERO_COPY_TX_DRIVER != 0 )
  693. {
  694. if( xDoRelease == pdFALSE )
  695. {
  696. pxNetworkBuffer = pxDuplicateNetworkBufferWithDescriptor( pxNetworkBuffer, ( size_t ) pxNetworkBuffer->xDataLength );
  697. if( pxNetworkBuffer == NULL )
  698. {
  699. FreeRTOS_debug_printf( ( "prvTCPReturnPacket: duplicate failed\n" ) );
  700. }
  701. xDoRelease = pdTRUE;
  702. }
  703. }
  704. #endif /* ipconfigZERO_COPY_TX_DRIVER */
  705. #ifndef __COVERITY__
  706. if( pxNetworkBuffer != NULL )
  707. #endif
  708. {
  709. /* Map the ethernet buffer onto a TCPPacket_t struct for easy access to the fields. */
  710. pxTCPPacket = ipCAST_PTR_TO_TYPE_PTR( TCPPacket_t, pxNetworkBuffer->pucEthernetBuffer );
  711. pxIPHeader = &pxTCPPacket->xIPHeader;
  712. pxEthernetHeader = &pxTCPPacket->xEthernetHeader;
  713. /* Fill the packet, using hton translations. */
  714. if( pxSocket != NULL )
  715. {
  716. /* Calculate the space in the RX buffer in order to advertise the
  717. * size of this socket's reception window. */
  718. pxTCPWindow = &( pxSocket->u.xTCP.xTCPWindow );
  719. if( pxSocket->u.xTCP.rxStream != NULL )
  720. {
  721. /* An RX stream was created already, see how much space is
  722. * available. */
  723. ulFrontSpace = ( uint32_t ) uxStreamBufferFrontSpace( pxSocket->u.xTCP.rxStream );
  724. }
  725. else
  726. {
  727. /* No RX stream has been created, the full stream size is
  728. * available. */
  729. ulFrontSpace = ( uint32_t ) pxSocket->u.xTCP.uxRxStreamSize;
  730. }
  731. /* Take the minimum of the RX buffer space and the RX window size. */
  732. ulSpace = FreeRTOS_min_uint32( pxTCPWindow->xSize.ulRxWindowLength, ulFrontSpace );
  733. if( ( pxSocket->u.xTCP.bits.bLowWater != pdFALSE_UNSIGNED ) || ( pxSocket->u.xTCP.bits.bRxStopped != pdFALSE_UNSIGNED ) )
  734. {
  735. /* The low-water mark was reached, meaning there was little
  736. * space left. The socket will wait until the application has read
  737. * or flushed the incoming data, and 'zero-window' will be
  738. * advertised. */
  739. ulSpace = 0U;
  740. }
  741. /* If possible, advertise an RX window size of at least 1 MSS, otherwise
  742. * the peer might start 'zero window probing', i.e. sending small packets
  743. * (1, 2, 4, 8... bytes). */
  744. if( ( ulSpace < pxSocket->u.xTCP.usCurMSS ) && ( ulFrontSpace >= pxSocket->u.xTCP.usCurMSS ) )
  745. {
  746. ulSpace = pxSocket->u.xTCP.usCurMSS;
  747. }
  748. /* Avoid overflow of the 16-bit win field. */
  749. #if ( ipconfigUSE_TCP_WIN != 0 )
  750. {
  751. ulWinSize = ( ulSpace >> pxSocket->u.xTCP.ucMyWinScaleFactor );
  752. }
  753. #else
  754. {
  755. ulWinSize = ulSpace;
  756. }
  757. #endif
  758. if( ulWinSize > 0xfffcUL )
  759. {
  760. ulWinSize = 0xfffcUL;
  761. }
  762. pxTCPPacket->xTCPHeader.usWindow = FreeRTOS_htons( ( uint16_t ) ulWinSize );
  763. /* The new window size has been advertised, switch off the flag. */
  764. pxSocket->u.xTCP.bits.bWinChange = pdFALSE_UNSIGNED;
  765. /* Later on, when deciding to delay an ACK, a precise estimate is needed
  766. * of the free RX space. At this moment, 'ulHighestRxAllowed' would be the
  767. * highest sequence number minus 1 that the socket will accept. */
  768. pxSocket->u.xTCP.ulHighestRxAllowed = pxTCPWindow->rx.ulCurrentSequenceNumber + ulSpace;
  769. #if ( ipconfigTCP_KEEP_ALIVE == 1 )
  770. if( pxSocket->u.xTCP.bits.bSendKeepAlive != pdFALSE_UNSIGNED )
  771. {
  772. /* Sending a keep-alive packet, send the current sequence number
  773. * minus 1, which will be recognised as a keep-alive packet and
  774. * responded to by acknowledging the last byte. */
  775. pxSocket->u.xTCP.bits.bSendKeepAlive = pdFALSE_UNSIGNED;
  776. pxSocket->u.xTCP.bits.bWaitKeepAlive = pdTRUE_UNSIGNED;
  777. pxTCPPacket->xTCPHeader.ulSequenceNumber = pxSocket->u.xTCP.xTCPWindow.ulOurSequenceNumber - 1UL;
  778. pxTCPPacket->xTCPHeader.ulSequenceNumber = FreeRTOS_htonl( pxTCPPacket->xTCPHeader.ulSequenceNumber );
  779. }
  780. else
  781. #endif /* if ( ipconfigTCP_KEEP_ALIVE == 1 ) */
  782. {
  783. pxTCPPacket->xTCPHeader.ulSequenceNumber = FreeRTOS_htonl( pxSocket->u.xTCP.xTCPWindow.ulOurSequenceNumber );
  784. if( ( pxTCPPacket->xTCPHeader.ucTCPFlags & ( uint8_t ) tcpTCP_FLAG_FIN ) != 0U )
  785. {
  786. /* Suppress FIN in case this packet carries earlier data to be
  787. * retransmitted. */
  788. uint32_t ulDataLen = ( uint32_t ) ( ulLen - ( ipSIZE_OF_TCP_HEADER + ipSIZE_OF_IPv4_HEADER ) );
  789. if( ( pxTCPWindow->ulOurSequenceNumber + ulDataLen ) != pxTCPWindow->tx.ulFINSequenceNumber )
  790. {
  791. pxTCPPacket->xTCPHeader.ucTCPFlags &= ( ( uint8_t ) ~tcpTCP_FLAG_FIN );
  792. FreeRTOS_debug_printf( ( "Suppress FIN for %lu + %lu < %lu\n",
  793. pxTCPWindow->ulOurSequenceNumber - pxTCPWindow->tx.ulFirstSequenceNumber,
  794. ulDataLen,
  795. pxTCPWindow->tx.ulFINSequenceNumber - pxTCPWindow->tx.ulFirstSequenceNumber ) );
  796. }
  797. }
  798. }
  799. /* Tell which sequence number is expected next time */
  800. pxTCPPacket->xTCPHeader.ulAckNr = FreeRTOS_htonl( pxTCPWindow->rx.ulCurrentSequenceNumber );
  801. }
  802. else
  803. {
  804. /* Sending data without a socket, probably replying with a RST flag
  805. * Just swap the two sequence numbers. */
  806. vFlip_32( pxTCPPacket->xTCPHeader.ulSequenceNumber, pxTCPPacket->xTCPHeader.ulAckNr );
  807. }
  808. pxIPHeader->ucTimeToLive = ( uint8_t ) ipconfigTCP_TIME_TO_LIVE;
  809. pxIPHeader->usLength = FreeRTOS_htons( ulLen );
  810. if( ( pxSocket == NULL ) || ( *ipLOCAL_IP_ADDRESS_POINTER == 0UL ) )
  811. {
  812. /* When pxSocket is NULL, this function is called by prvTCPSendReset()
  813. * and the IP-addresses must be swapped.
  814. * Also swap the IP-addresses in case the IP-tack doesn't have an
  815. * IP-address yet, i.e. when ( *ipLOCAL_IP_ADDRESS_POINTER == 0UL ). */
  816. ulSourceAddress = pxIPHeader->ulDestinationIPAddress;
  817. }
  818. else
  819. {
  820. ulSourceAddress = *ipLOCAL_IP_ADDRESS_POINTER;
  821. }
  822. pxIPHeader->ulDestinationIPAddress = pxIPHeader->ulSourceIPAddress;
  823. pxIPHeader->ulSourceIPAddress = ulSourceAddress;
  824. vFlip_16( pxTCPPacket->xTCPHeader.usSourcePort, pxTCPPacket->xTCPHeader.usDestinationPort );
  825. /* Just an increasing number. */
  826. pxIPHeader->usIdentification = FreeRTOS_htons( usPacketIdentifier );
  827. usPacketIdentifier++;
  828. pxIPHeader->usFragmentOffset = 0U;
  829. /* Important: tell NIC driver how many bytes must be sent. */
  830. pxNetworkBuffer->xDataLength = ulLen + ipSIZE_OF_ETH_HEADER;
  831. #if ( ipconfigDRIVER_INCLUDED_TX_IP_CHECKSUM == 0 )
  832. {
  833. /* calculate the IP header checksum, in case the driver won't do that. */
  834. pxIPHeader->usHeaderChecksum = 0x00U;
  835. pxIPHeader->usHeaderChecksum = usGenerateChecksum( 0U, ( uint8_t * ) &( pxIPHeader->ucVersionHeaderLength ), ipSIZE_OF_IPv4_HEADER );
  836. pxIPHeader->usHeaderChecksum = ~FreeRTOS_htons( pxIPHeader->usHeaderChecksum );
  837. /* calculate the TCP checksum for an outgoing packet. */
  838. ( void ) usGenerateProtocolChecksum( ( uint8_t * ) pxTCPPacket, pxNetworkBuffer->xDataLength, pdTRUE );
  839. /* A calculated checksum of 0 must be inverted as 0 means the checksum
  840. * is disabled. */
  841. if( pxTCPPacket->xTCPHeader.usChecksum == 0U )
  842. {
  843. pxTCPPacket->xTCPHeader.usChecksum = 0xffffU;
  844. }
  845. }
  846. #endif /* if ( ipconfigDRIVER_INCLUDED_TX_IP_CHECKSUM == 0 ) */
  847. #if ( ipconfigUSE_LINKED_RX_MESSAGES != 0 )
  848. {
  849. pxNetworkBuffer->pxNextBuffer = NULL;
  850. }
  851. #endif
  852. /* Fill in the destination MAC addresses. */
  853. ( void ) memcpy( ( void * ) ( &( pxEthernetHeader->xDestinationAddress ) ),
  854. ( const void * ) ( &( pxEthernetHeader->xSourceAddress ) ),
  855. sizeof( pxEthernetHeader->xDestinationAddress ) );
  856. /*
  857. * Use helper variables for memcpy() to remain
  858. * compliant with MISRA Rule 21.15. These should be
  859. * optimized away.
  860. */
  861. /* The source MAC addresses is fixed to 'ipLOCAL_MAC_ADDRESS'. */
  862. pvCopySource = ipLOCAL_MAC_ADDRESS;
  863. pvCopyDest = &pxEthernetHeader->xSourceAddress;
  864. ( void ) memcpy( pvCopyDest, pvCopySource, ( size_t ) ipMAC_ADDRESS_LENGTH_BYTES );
  865. #if defined( ipconfigETHERNET_MINIMUM_PACKET_BYTES )
  866. {
  867. if( pxNetworkBuffer->xDataLength < ( size_t ) ipconfigETHERNET_MINIMUM_PACKET_BYTES )
  868. {
  869. BaseType_t xIndex;
  870. for( xIndex = ( BaseType_t ) pxNetworkBuffer->xDataLength; xIndex < ( BaseType_t ) ipconfigETHERNET_MINIMUM_PACKET_BYTES; xIndex++ )
  871. {
  872. pxNetworkBuffer->pucEthernetBuffer[ xIndex ] = 0U;
  873. }
  874. pxNetworkBuffer->xDataLength = ( size_t ) ipconfigETHERNET_MINIMUM_PACKET_BYTES;
  875. }
  876. }
  877. #endif /* if defined( ipconfigETHERNET_MINIMUM_PACKET_BYTES ) */
  878. /* Send! */
  879. iptraceNETWORK_INTERFACE_OUTPUT( pxNetworkBuffer->xDataLength, pxNetworkBuffer->pucEthernetBuffer );
  880. ( void ) xNetworkInterfaceOutput( pxNetworkBuffer, xDoRelease );
  881. if( xDoRelease == pdFALSE )
  882. {
  883. /* Swap-back some fields, as pxBuffer probably points to a socket field
  884. * containing the packet header. */
  885. vFlip_16( pxTCPPacket->xTCPHeader.usSourcePort, pxTCPPacket->xTCPHeader.usDestinationPort );
  886. pxTCPPacket->xIPHeader.ulSourceIPAddress = pxTCPPacket->xIPHeader.ulDestinationIPAddress;
  887. ( void ) memcpy( ( void * ) ( pxEthernetHeader->xSourceAddress.ucBytes ), ( const void * ) ( pxEthernetHeader->xDestinationAddress.ucBytes ), ( size_t ) ipMAC_ADDRESS_LENGTH_BYTES );
  888. }
  889. else
  890. {
  891. /* Nothing to do: the buffer has been passed to DMA and will be released after use */
  892. }
  893. } /* if( pxNetworkBuffer != NULL ) */
  894. }
  895. /*-----------------------------------------------------------*/
  896. /**
  897. * @brief Create the TCP window for the given socket.
  898. *
  899. * @param[in] pxSocket: The socket for which the window is being created.
  900. *
  901. * @note The SYN event is very important: the sequence numbers, which have a kind of
  902. * random starting value, are being synchronized. The sliding window manager
  903. * (in FreeRTOS_TCP_WIN.c) needs to know them, along with the Maximum Segment
  904. * Size (MSS).
  905. */
  906. static void prvTCPCreateWindow( FreeRTOS_Socket_t * pxSocket )
  907. {
  908. if( xTCPWindowLoggingLevel != 0 )
  909. {
  910. FreeRTOS_debug_printf( ( "Limits (using): TCP Win size %u Water %u <= %u <= %u\n",
  911. ( unsigned ) pxSocket->u.xTCP.uxRxWinSize * ipconfigTCP_MSS,
  912. ( unsigned ) pxSocket->u.xTCP.uxLittleSpace,
  913. ( unsigned ) pxSocket->u.xTCP.uxEnoughSpace,
  914. ( unsigned ) pxSocket->u.xTCP.uxRxStreamSize ) );
  915. }
  916. vTCPWindowCreate(
  917. &pxSocket->u.xTCP.xTCPWindow,
  918. ipconfigTCP_MSS * pxSocket->u.xTCP.uxRxWinSize,
  919. ipconfigTCP_MSS * pxSocket->u.xTCP.uxTxWinSize,
  920. pxSocket->u.xTCP.xTCPWindow.rx.ulCurrentSequenceNumber,
  921. pxSocket->u.xTCP.xTCPWindow.ulOurSequenceNumber,
  922. ( uint32_t ) pxSocket->u.xTCP.usInitMSS );
  923. }
  924. /*-----------------------------------------------------------*/
  925. /**
  926. * @brief Let ARP look-up the MAC-address of the peer and initialise the first SYN
  927. * packet.
  928. *
  929. * @param[in] pxSocket: The socket owning the TCP connection. The first packet shall
  930. * be created in this socket.
  931. *
  932. * @return pdTRUE: if the packet was successfully created and the first SYN can be sent.
  933. * Else pdFALSE.
  934. *
  935. * @note Connecting sockets have a special state: eCONNECT_SYN. In this phase,
  936. * the Ethernet address of the target will be found using ARP. In case the
  937. * target IP address is not within the netmask, the hardware address of the
  938. * gateway will be used.
  939. */
  940. static BaseType_t prvTCPPrepareConnect( FreeRTOS_Socket_t * pxSocket )
  941. {
  942. TCPPacket_t * pxTCPPacket;
  943. IPHeader_t * pxIPHeader;
  944. eARPLookupResult_t eReturned;
  945. uint32_t ulRemoteIP;
  946. MACAddress_t xEthAddress;
  947. BaseType_t xReturn = pdTRUE;
  948. uint32_t ulInitialSequenceNumber = 0;
  949. #if ( ipconfigHAS_PRINTF != 0 )
  950. {
  951. /* Only necessary for nicer logging. */
  952. ( void ) memset( xEthAddress.ucBytes, 0, sizeof( xEthAddress.ucBytes ) );
  953. }
  954. #endif /* ipconfigHAS_PRINTF != 0 */
  955. ulRemoteIP = FreeRTOS_htonl( pxSocket->u.xTCP.ulRemoteIP );
  956. /* Determine the ARP cache status for the requested IP address. */
  957. eReturned = eARPGetCacheEntry( &( ulRemoteIP ), &( xEthAddress ) );
  958. switch( eReturned )
  959. {
  960. case eARPCacheHit: /* An ARP table lookup found a valid entry. */
  961. break; /* We can now prepare the SYN packet. */
  962. case eARPCacheMiss: /* An ARP table lookup did not find a valid entry. */
  963. case eCantSendPacket: /* There is no IP address, or an ARP is still in progress. */
  964. default:
  965. /* Count the number of times it could not find the ARP address. */
  966. pxSocket->u.xTCP.ucRepCount++;
  967. FreeRTOS_debug_printf( ( "ARP for %lxip (using %lxip): rc=%d %02X:%02X:%02X %02X:%02X:%02X\n",
  968. pxSocket->u.xTCP.ulRemoteIP,
  969. FreeRTOS_htonl( ulRemoteIP ),
  970. eReturned,
  971. xEthAddress.ucBytes[ 0 ],
  972. xEthAddress.ucBytes[ 1 ],
  973. xEthAddress.ucBytes[ 2 ],
  974. xEthAddress.ucBytes[ 3 ],
  975. xEthAddress.ucBytes[ 4 ],
  976. xEthAddress.ucBytes[ 5 ] ) );
  977. /* And issue a (new) ARP request */
  978. FreeRTOS_OutputARPRequest( ulRemoteIP );
  979. xReturn = pdFALSE;
  980. break;
  981. }
  982. if( xReturn != pdFALSE )
  983. {
  984. /* Get a difficult-to-predict initial sequence number for this 4-tuple. */
  985. ulInitialSequenceNumber = ulApplicationGetNextSequenceNumber( *ipLOCAL_IP_ADDRESS_POINTER,
  986. pxSocket->usLocalPort,
  987. pxSocket->u.xTCP.ulRemoteIP,
  988. pxSocket->u.xTCP.usRemotePort );
  989. /* Check for a random number generation error. */
  990. if( ulInitialSequenceNumber == 0UL )
  991. {
  992. xReturn = pdFALSE;
  993. }
  994. }
  995. if( xReturn != pdFALSE )
  996. {
  997. uint16_t usLength;
  998. /* The MAC-address of the peer (or gateway) has been found,
  999. * now prepare the initial TCP packet and some fields in the socket. Map
  1000. * the buffer onto the TCPPacket_t struct to easily access it's field. */
  1001. pxTCPPacket = ipCAST_PTR_TO_TYPE_PTR( TCPPacket_t, pxSocket->u.xTCP.xPacket.u.ucLastPacket );
  1002. pxIPHeader = &pxTCPPacket->xIPHeader;
  1003. /* reset the retry counter to zero. */
  1004. pxSocket->u.xTCP.ucRepCount = 0U;
  1005. /* And remember that the connect/SYN data are prepared. */
  1006. pxSocket->u.xTCP.bits.bConnPrepared = pdTRUE_UNSIGNED;
  1007. /* Now that the Ethernet address is known, the initial packet can be
  1008. * prepared. */
  1009. ( void ) memset( pxSocket->u.xTCP.xPacket.u.ucLastPacket, 0, sizeof( pxSocket->u.xTCP.xPacket.u.ucLastPacket ) );
  1010. /* Write the Ethernet address in Source, because it will be swapped by
  1011. * prvTCPReturnPacket(). */
  1012. ( void ) memcpy( ( void * ) ( &pxTCPPacket->xEthernetHeader.xSourceAddress ), ( const void * ) ( &xEthAddress ), sizeof( xEthAddress ) );
  1013. /* 'ipIPv4_FRAME_TYPE' is already in network-byte-order. */
  1014. pxTCPPacket->xEthernetHeader.usFrameType = ipIPv4_FRAME_TYPE;
  1015. pxIPHeader->ucVersionHeaderLength = 0x45U;
  1016. usLength = ( uint16_t ) ( sizeof( TCPPacket_t ) - sizeof( pxTCPPacket->xEthernetHeader ) );
  1017. pxIPHeader->usLength = FreeRTOS_htons( usLength );
  1018. pxIPHeader->ucTimeToLive = ( uint8_t ) ipconfigTCP_TIME_TO_LIVE;
  1019. pxIPHeader->ucProtocol = ( uint8_t ) ipPROTOCOL_TCP;
  1020. /* Addresses and ports will be stored swapped because prvTCPReturnPacket
  1021. * will swap them back while replying. */
  1022. pxIPHeader->ulDestinationIPAddress = *ipLOCAL_IP_ADDRESS_POINTER;
  1023. pxIPHeader->ulSourceIPAddress = FreeRTOS_htonl( pxSocket->u.xTCP.ulRemoteIP );
  1024. pxTCPPacket->xTCPHeader.usSourcePort = FreeRTOS_htons( pxSocket->u.xTCP.usRemotePort );
  1025. pxTCPPacket->xTCPHeader.usDestinationPort = FreeRTOS_htons( pxSocket->usLocalPort );
  1026. /* We are actively connecting, so the peer's Initial Sequence Number (ISN)
  1027. * isn't known yet. */
  1028. pxSocket->u.xTCP.xTCPWindow.rx.ulCurrentSequenceNumber = 0UL;
  1029. /* Start with ISN (Initial Sequence Number). */
  1030. pxSocket->u.xTCP.xTCPWindow.ulOurSequenceNumber = ulInitialSequenceNumber;
  1031. /* The TCP header size is 20 bytes, divided by 4 equals 5, which is put in
  1032. * the high nibble of the TCP offset field. */
  1033. pxTCPPacket->xTCPHeader.ucTCPOffset = 0x50U;
  1034. /* Only set the SYN flag. */
  1035. pxTCPPacket->xTCPHeader.ucTCPFlags = tcpTCP_FLAG_SYN;
  1036. /* Set the values of usInitMSS / usCurMSS for this socket. */
  1037. prvSocketSetMSS( pxSocket );
  1038. /* The initial sequence numbers at our side are known. Later
  1039. * vTCPWindowInit() will be called to fill in the peer's sequence numbers, but
  1040. * first wait for a SYN+ACK reply. */
  1041. prvTCPCreateWindow( pxSocket );
  1042. }
  1043. return xReturn;
  1044. }
  1045. /*-----------------------------------------------------------*/
  1046. /* For logging and debugging: make a string showing the TCP flags
  1047. */
  1048. #if ( ipconfigHAS_DEBUG_PRINTF != 0 )
  1049. /**
  1050. * @brief Print out the value of flags in a human readable manner.
  1051. *
  1052. * @param[in] xFlags: The TCP flags.
  1053. *
  1054. * @return The string containing the flags.
  1055. */
  1056. static const char * prvTCPFlagMeaning( UBaseType_t xFlags )
  1057. {
  1058. static char retString[ 10 ];
  1059. size_t uxFlags = ( size_t ) xFlags;
  1060. ( void ) snprintf( retString,
  1061. sizeof( retString ), "%c%c%c%c%c%c%c%c",
  1062. ( ( uxFlags & ( size_t ) tcpTCP_FLAG_FIN ) != 0 ) ? 'F' : '.', /* 0x0001: No more data from sender */
  1063. ( ( uxFlags & ( size_t ) tcpTCP_FLAG_SYN ) != 0 ) ? 'S' : '.', /* 0x0002: Synchronize sequence numbers */
  1064. ( ( uxFlags & ( size_t ) tcpTCP_FLAG_RST ) != 0 ) ? 'R' : '.', /* 0x0004: Reset the connection */
  1065. ( ( uxFlags & ( size_t ) tcpTCP_FLAG_PSH ) != 0 ) ? 'P' : '.', /* 0x0008: Push function: please push buffered data to the recv application */
  1066. ( ( uxFlags & ( size_t ) tcpTCP_FLAG_ACK ) != 0 ) ? 'A' : '.', /* 0x0010: Acknowledgment field is significant */
  1067. ( ( uxFlags & ( size_t ) tcpTCP_FLAG_URG ) != 0 ) ? 'U' : '.', /* 0x0020: Urgent pointer field is significant */
  1068. ( ( uxFlags & ( size_t ) tcpTCP_FLAG_ECN ) != 0 ) ? 'E' : '.', /* 0x0040: ECN-Echo */
  1069. ( ( uxFlags & ( size_t ) tcpTCP_FLAG_CWR ) != 0 ) ? 'C' : '.' ); /* 0x0080: Congestion Window Reduced */
  1070. return retString;
  1071. }
  1072. /*-----------------------------------------------------------*/
  1073. #endif /* ipconfigHAS_DEBUG_PRINTF */
  1074. /**
  1075. * @brief Parse the TCP option(s) received, if present.
  1076. *
  1077. * @param[in] pxSocket: The socket handling the connection.
  1078. * @param[in] pxNetworkBuffer: The network buffer containing the TCP
  1079. * packet.
  1080. *
  1081. * @note It has already been verified that:
  1082. * ((pxTCPHeader->ucTCPOffset & 0xf0) > 0x50), meaning that
  1083. * the TP header is longer than the usual 20 (5 x 4) bytes.
  1084. */
  1085. _static void prvCheckOptions( FreeRTOS_Socket_t * pxSocket,
  1086. const NetworkBufferDescriptor_t * pxNetworkBuffer )
  1087. {
  1088. size_t uxTCPHeaderOffset = ipSIZE_OF_ETH_HEADER + xIPHeaderSize( pxNetworkBuffer );
  1089. const ProtocolHeaders_t * pxProtocolHeaders = ipCAST_PTR_TO_TYPE_PTR( ProtocolHeaders_t,
  1090. &( pxNetworkBuffer->pucEthernetBuffer[ uxTCPHeaderOffset ] ) );
  1091. const TCPHeader_t * pxTCPHeader;
  1092. const uint8_t * pucPtr;
  1093. BaseType_t xHasSYNFlag;
  1094. /* Offset in the network packet where the first option byte is stored. */
  1095. size_t uxOptionOffset = uxTCPHeaderOffset + ( sizeof( TCPHeader_t ) - sizeof( pxTCPHeader->ucOptdata ) );
  1096. size_t uxOptionsLength;
  1097. size_t uxResult;
  1098. uint8_t ucLength;
  1099. pxTCPHeader = &( pxProtocolHeaders->xTCPHeader );
  1100. /* A character pointer to iterate through the option data */
  1101. pucPtr = pxTCPHeader->ucOptdata;
  1102. if( pxTCPHeader->ucTCPOffset <= ( 5U << 4U ) )
  1103. {
  1104. /* Avoid integer underflow in computation of ucLength. */
  1105. }
  1106. else
  1107. {
  1108. ucLength = ( ( ( pxTCPHeader->ucTCPOffset >> 4U ) - 5U ) << 2U );
  1109. uxOptionsLength = ( size_t ) ucLength;
  1110. if( pxNetworkBuffer->xDataLength > uxOptionOffset )
  1111. {
  1112. /* Validate options size calculation. */
  1113. if( ( pxNetworkBuffer->xDataLength > uxOptionOffset ) &&
  1114. ( uxOptionsLength <= ( pxNetworkBuffer->xDataLength - uxOptionOffset ) ) )
  1115. {
  1116. if( ( pxTCPHeader->ucTCPFlags & tcpTCP_FLAG_SYN ) != ( uint8_t ) 0U )
  1117. {
  1118. xHasSYNFlag = pdTRUE;
  1119. }
  1120. else
  1121. {
  1122. xHasSYNFlag = pdFALSE;
  1123. }
  1124. /* The length check is only necessary in case the option data are
  1125. * corrupted, we don't like to run into invalid memory and crash. */
  1126. for( ; ; )
  1127. {
  1128. if( uxOptionsLength == 0U )
  1129. {
  1130. /* coverity[break_stmt] : Break statement terminating the loop */
  1131. break;
  1132. }
  1133. uxResult = prvSingleStepTCPHeaderOptions( pucPtr, uxOptionsLength, pxSocket, xHasSYNFlag );
  1134. if( uxResult == 0UL )
  1135. {
  1136. break;
  1137. }
  1138. uxOptionsLength -= uxResult;
  1139. pucPtr = &( pucPtr[ uxResult ] );
  1140. }
  1141. }
  1142. }
  1143. }
  1144. }
  1145. /*-----------------------------------------------------------*/
  1146. /**
  1147. * @brief Identify and deal with a single TCP header option, advancing the pointer to
  1148. * the header.
  1149. *
  1150. * @param[in] pucPtr: Pointer to the TCP packet options.
  1151. * @param[in] uxTotalLength: Length of the TCP packet options.
  1152. * @param[in] pxSocket: Socket handling the connection.
  1153. * @param[in] xHasSYNFlag: Whether the header has SYN flag or not.
  1154. *
  1155. * @return This function returns pdTRUE or pdFALSE depending on whether the caller
  1156. * should continue to parse more header options or break the loop.
  1157. */
  1158. _static size_t prvSingleStepTCPHeaderOptions( const uint8_t * const pucPtr,
  1159. size_t uxTotalLength,
  1160. FreeRTOS_Socket_t * const pxSocket,
  1161. BaseType_t xHasSYNFlag )
  1162. {
  1163. UBaseType_t uxNewMSS;
  1164. size_t uxRemainingOptionsBytes = uxTotalLength;
  1165. uint8_t ucLen;
  1166. size_t uxIndex;
  1167. TCPWindow_t * pxTCPWindow = &( pxSocket->u.xTCP.xTCPWindow );
  1168. BaseType_t xReturn = pdFALSE;
  1169. if( pucPtr[ 0U ] == tcpTCP_OPT_END )
  1170. {
  1171. /* End of options. */
  1172. uxIndex = 0U;
  1173. }
  1174. else if( pucPtr[ 0U ] == tcpTCP_OPT_NOOP )
  1175. {
  1176. /* NOP option, inserted to make the length a multiple of 4. */
  1177. uxIndex = 1U;
  1178. }
  1179. else if( uxRemainingOptionsBytes < 2U )
  1180. {
  1181. /* Any other well-formed option must be at least two bytes: the option
  1182. * type byte followed by a length byte. */
  1183. uxIndex = 0U;
  1184. }
  1185. #if ( ipconfigUSE_TCP_WIN != 0 )
  1186. else if( pucPtr[ 0 ] == tcpTCP_OPT_WSOPT )
  1187. {
  1188. /* The TCP Window Scale Option. */
  1189. /* Confirm that the option fits in the remaining buffer space. */
  1190. if( ( uxRemainingOptionsBytes < tcpTCP_OPT_WSOPT_LEN ) || ( pucPtr[ 1 ] != tcpTCP_OPT_WSOPT_LEN ) )
  1191. {
  1192. uxIndex = 0U;
  1193. }
  1194. else
  1195. {
  1196. /* Option is only valid in SYN phase. */
  1197. if( xHasSYNFlag != 0 )
  1198. {
  1199. pxSocket->u.xTCP.ucPeerWinScaleFactor = pucPtr[ 2 ];
  1200. pxSocket->u.xTCP.bits.bWinScaling = pdTRUE_UNSIGNED;
  1201. }
  1202. uxIndex = tcpTCP_OPT_WSOPT_LEN;
  1203. }
  1204. }
  1205. #endif /* ipconfigUSE_TCP_WIN */
  1206. else if( pucPtr[ 0 ] == tcpTCP_OPT_MSS )
  1207. {
  1208. /* Confirm that the option fits in the remaining buffer space. */
  1209. if( ( uxRemainingOptionsBytes < tcpTCP_OPT_MSS_LEN ) || ( pucPtr[ 1 ] != tcpTCP_OPT_MSS_LEN ) )
  1210. {
  1211. uxIndex = 0U;
  1212. }
  1213. else
  1214. {
  1215. /* An MSS option with the correct option length. FreeRTOS_htons()
  1216. * is not needed here because usChar2u16() already returns a host
  1217. * endian number. */
  1218. uxNewMSS = usChar2u16( &( pucPtr[ 2 ] ) );
  1219. if( pxSocket->u.xTCP.usInitMSS != uxNewMSS )
  1220. {
  1221. /* Perform a basic check on the the new MSS. */
  1222. if( uxNewMSS == 0U )
  1223. {
  1224. uxIndex = 0U;
  1225. /* Return Condition found. */
  1226. xReturn = pdTRUE;
  1227. }
  1228. else
  1229. {
  1230. FreeRTOS_debug_printf( ( "MSS change %u -> %lu\n", pxSocket->u.xTCP.usInitMSS, uxNewMSS ) );
  1231. }
  1232. }
  1233. /* If a 'return' condition has not been found. */
  1234. if( xReturn == pdFALSE )
  1235. {
  1236. if( pxSocket->u.xTCP.usInitMSS > uxNewMSS )
  1237. {
  1238. /* our MSS was bigger than the MSS of the other party: adapt it. */
  1239. pxSocket->u.xTCP.bits.bMssChange = pdTRUE_UNSIGNED;
  1240. if( pxSocket->u.xTCP.usCurMSS > uxNewMSS )
  1241. {
  1242. /* The peer advertises a smaller MSS than this socket was
  1243. * using. Use that as well. */
  1244. FreeRTOS_debug_printf( ( "Change mss %d => %lu\n", pxSocket->u.xTCP.usCurMSS, uxNewMSS ) );
  1245. pxSocket->u.xTCP.usCurMSS = ( uint16_t ) uxNewMSS;
  1246. }
  1247. pxTCPWindow->xSize.ulRxWindowLength = ( ( uint32_t ) uxNewMSS ) * ( pxTCPWindow->xSize.ulRxWindowLength / ( ( uint32_t ) uxNewMSS ) );
  1248. pxTCPWindow->usMSSInit = ( uint16_t ) uxNewMSS;
  1249. pxTCPWindow->usMSS = ( uint16_t ) uxNewMSS;
  1250. pxSocket->u.xTCP.usInitMSS = ( uint16_t ) uxNewMSS;
  1251. pxSocket->u.xTCP.usCurMSS = ( uint16_t ) uxNewMSS;
  1252. }
  1253. uxIndex = tcpTCP_OPT_MSS_LEN;
  1254. }
  1255. }
  1256. }
  1257. else
  1258. {
  1259. /* All other options have a length field, so that we easily
  1260. * can skip past them. */
  1261. ucLen = pucPtr[ 1 ];
  1262. uxIndex = 0U;
  1263. if( ( ucLen < ( uint8_t ) 2U ) || ( uxRemainingOptionsBytes < ( size_t ) ucLen ) )
  1264. {
  1265. /* If the length field is too small or too big, the options are
  1266. * malformed, don't process them further.
  1267. */
  1268. }
  1269. else
  1270. {
  1271. #if ( ipconfigUSE_TCP_WIN == 1 )
  1272. {
  1273. /* Selective ACK: the peer has received a packet but it is missing
  1274. * earlier packets. At least this packet does not need retransmission
  1275. * anymore. ulTCPWindowTxSack( ) takes care of this administration.
  1276. */
  1277. if( pucPtr[ 0U ] == tcpTCP_OPT_SACK_A )
  1278. {
  1279. ucLen -= 2U;
  1280. uxIndex += 2U;
  1281. while( ucLen >= ( uint8_t ) 8U )
  1282. {
  1283. prvReadSackOption( pucPtr, uxIndex, pxSocket );
  1284. uxIndex += 8U;
  1285. ucLen -= 8U;
  1286. }
  1287. /* ucLen should be 0 by now. */
  1288. }
  1289. }
  1290. #endif /* ipconfigUSE_TCP_WIN == 1 */
  1291. uxIndex += ( size_t ) ucLen;
  1292. }
  1293. }
  1294. return uxIndex;
  1295. }
  1296. /*-----------------------------------------------------------*/
  1297. #if ( ipconfigUSE_TCP_WIN == 1 )
  1298. /**
  1299. * @brief Skip past TCP header options when doing Selective ACK, until there are no
  1300. * more options left.
  1301. *
  1302. * @param[in] pucPtr: Pointer to the TCP packet options.
  1303. * @param[in] uxIndex: Index of options in the TCP packet options.
  1304. * @param[in] pxSocket: Socket handling the TCP connection.
  1305. */
  1306. _static void prvReadSackOption( const uint8_t * const pucPtr,
  1307. size_t uxIndex,
  1308. FreeRTOS_Socket_t * const pxSocket )
  1309. {
  1310. uint32_t ulFirst = ulChar2u32( &( pucPtr[ uxIndex ] ) );
  1311. uint32_t ulLast = ulChar2u32( &( pucPtr[ uxIndex + 4U ] ) );
  1312. uint32_t ulCount = ulTCPWindowTxSack( &( pxSocket->u.xTCP.xTCPWindow ), ulFirst, ulLast );
  1313. /* ulTCPWindowTxSack( ) returns the number of bytes which have been acked
  1314. * starting from the head position. Advance the tail pointer in txStream.
  1315. */
  1316. if( ( pxSocket->u.xTCP.txStream != NULL ) && ( ulCount > 0U ) )
  1317. {
  1318. /* Just advancing the tail index, 'ulCount' bytes have been confirmed. */
  1319. ( void ) uxStreamBufferGet( pxSocket->u.xTCP.txStream, 0, NULL, ( size_t ) ulCount, pdFALSE );
  1320. pxSocket->xEventBits |= ( EventBits_t ) eSOCKET_SEND;
  1321. #if ipconfigSUPPORT_SELECT_FUNCTION == 1
  1322. {
  1323. if( ( pxSocket->xSelectBits & ( EventBits_t ) eSELECT_WRITE ) != 0U )
  1324. {
  1325. /* The field 'xEventBits' is used to store regular socket events
  1326. * (at most 8), as well as 'select events', which will be left-shifted.
  1327. */
  1328. pxSocket->xEventBits |= ( ( EventBits_t ) eSELECT_WRITE ) << SOCKET_EVENT_BIT_COUNT;
  1329. }
  1330. }
  1331. #endif
  1332. /* In case the socket owner has installed an OnSent handler,
  1333. * call it now. */
  1334. #if ( ipconfigUSE_CALLBACKS == 1 )
  1335. {
  1336. if( ipconfigIS_VALID_PROG_ADDRESS( pxSocket->u.xTCP.pxHandleSent ) )
  1337. {
  1338. pxSocket->u.xTCP.pxHandleSent( pxSocket, ulCount );
  1339. }
  1340. }
  1341. #endif /* ipconfigUSE_CALLBACKS == 1 */
  1342. }
  1343. }
  1344. #endif /* ( ipconfigUSE_TCP_WIN != 0 ) */
  1345. /*-----------------------------------------------------------*/
  1346. #if ( ipconfigUSE_TCP_WIN != 0 )
  1347. /**
  1348. * @brief Get the window scaling factor for the TCP connection.
  1349. *
  1350. * @param[in] pxSocket: The socket owning the TCP connection.
  1351. *
  1352. * @return The scaling factor.
  1353. */
  1354. static uint8_t prvWinScaleFactor( const FreeRTOS_Socket_t * pxSocket )
  1355. {
  1356. size_t uxWinSize;
  1357. uint8_t ucFactor;
  1358. /* 'xTCP.uxRxWinSize' is the size of the reception window in units of MSS. */
  1359. uxWinSize = pxSocket->u.xTCP.uxRxWinSize * ( size_t ) pxSocket->u.xTCP.usInitMSS;
  1360. ucFactor = 0U;
  1361. while( uxWinSize > 0xffffUL )
  1362. {
  1363. /* Divide by two and increase the binary factor by 1. */
  1364. uxWinSize >>= 1;
  1365. ucFactor++;
  1366. }
  1367. FreeRTOS_debug_printf( ( "prvWinScaleFactor: uxRxWinSize %u MSS %u Factor %u\n",
  1368. ( unsigned ) pxSocket->u.xTCP.uxRxWinSize,
  1369. ( unsigned ) pxSocket->u.xTCP.usInitMSS,
  1370. ucFactor ) );
  1371. return ucFactor;
  1372. }
  1373. #endif /* if ( ipconfigUSE_TCP_WIN != 0 ) */
  1374. /*-----------------------------------------------------------*/
  1375. /**
  1376. * @brief When opening a TCP connection, while SYN's are being sent, the parties may
  1377. * communicate what MSS (Maximum Segment Size) they intend to use, whether Selective
  1378. * ACK's ( SACK ) are supported, and the size of the reception window ( WSOPT ).
  1379. *
  1380. * @param[in] pxSocket: The socket being used for communication. It is used to set
  1381. * the MSS.
  1382. * @param[in,out] pxTCPHeader: The TCP packet header being used in the SYN transmission.
  1383. * The MSS and corresponding options shall be set in this
  1384. * header itself.
  1385. *
  1386. * @return The option length after the TCP header was updated.
  1387. *
  1388. * @note MSS is the net size of the payload, an is always smaller than MTU.
  1389. */
  1390. static UBaseType_t prvSetSynAckOptions( FreeRTOS_Socket_t * pxSocket,
  1391. TCPHeader_t * pxTCPHeader )
  1392. {
  1393. uint16_t usMSS = pxSocket->u.xTCP.usInitMSS;
  1394. UBaseType_t uxOptionsLength;
  1395. /* We send out the TCP Maximum Segment Size option with our SYN[+ACK]. */
  1396. pxTCPHeader->ucOptdata[ 0 ] = ( uint8_t ) tcpTCP_OPT_MSS;
  1397. pxTCPHeader->ucOptdata[ 1 ] = ( uint8_t ) tcpTCP_OPT_MSS_LEN;
  1398. pxTCPHeader->ucOptdata[ 2 ] = ( uint8_t ) ( usMSS >> 8 );
  1399. pxTCPHeader->ucOptdata[ 3 ] = ( uint8_t ) ( usMSS & 0xffU );
  1400. #if ( ipconfigUSE_TCP_WIN != 0 )
  1401. {
  1402. pxSocket->u.xTCP.ucMyWinScaleFactor = prvWinScaleFactor( pxSocket );
  1403. pxTCPHeader->ucOptdata[ 4 ] = tcpTCP_OPT_NOOP;
  1404. pxTCPHeader->ucOptdata[ 5 ] = ( uint8_t ) ( tcpTCP_OPT_WSOPT );
  1405. pxTCPHeader->ucOptdata[ 6 ] = ( uint8_t ) ( tcpTCP_OPT_WSOPT_LEN );
  1406. pxTCPHeader->ucOptdata[ 7 ] = ( uint8_t ) pxSocket->u.xTCP.ucMyWinScaleFactor;
  1407. uxOptionsLength = 8U;
  1408. }
  1409. #else
  1410. {
  1411. uxOptionsLength = 4U;
  1412. }
  1413. #endif /* if ( ipconfigUSE_TCP_WIN != 0 ) */
  1414. #if ( ipconfigUSE_TCP_WIN != 0 )
  1415. {
  1416. pxTCPHeader->ucOptdata[ uxOptionsLength ] = tcpTCP_OPT_NOOP;
  1417. pxTCPHeader->ucOptdata[ uxOptionsLength + 1U ] = tcpTCP_OPT_NOOP;
  1418. pxTCPHeader->ucOptdata[ uxOptionsLength + 2U ] = tcpTCP_OPT_SACK_P; /* 4: Sack-Permitted Option. */
  1419. pxTCPHeader->ucOptdata[ uxOptionsLength + 3U ] = 2U; /* 2: length of this option. */
  1420. uxOptionsLength += 4U;
  1421. }
  1422. #endif /* ipconfigUSE_TCP_WIN == 0 */
  1423. return uxOptionsLength; /* bytes, not words. */
  1424. }
  1425. /**
  1426. * @brief 'Touch' the socket to keep it alive/updated.
  1427. *
  1428. * @param[in] pxSocket: The socket to be updated.
  1429. *
  1430. * @note This is used for anti-hanging protection and TCP keep-alive messages.
  1431. * Called in two places: after receiving a packet and after a state change.
  1432. * The socket's alive timer may be reset.
  1433. */
  1434. static void prvTCPTouchSocket( FreeRTOS_Socket_t * pxSocket )
  1435. {
  1436. #if ( ipconfigTCP_HANG_PROTECTION == 1 )
  1437. {
  1438. pxSocket->u.xTCP.xLastActTime = xTaskGetTickCount();
  1439. }
  1440. #endif
  1441. #if ( ipconfigTCP_KEEP_ALIVE == 1 )
  1442. {
  1443. pxSocket->u.xTCP.bits.bWaitKeepAlive = pdFALSE_UNSIGNED;
  1444. pxSocket->u.xTCP.bits.bSendKeepAlive = pdFALSE_UNSIGNED;
  1445. pxSocket->u.xTCP.ucKeepRepCount = 0U;
  1446. pxSocket->u.xTCP.xLastAliveTime = xTaskGetTickCount();
  1447. }
  1448. #endif
  1449. ( void ) pxSocket;
  1450. }
  1451. /*-----------------------------------------------------------*/
  1452. /**
  1453. * @brief Changing to a new state. Centralised here to do specific actions such as
  1454. * resetting the alive timer, calling the user's OnConnect handler to notify
  1455. * that a socket has got (dis)connected, and setting bit to unblock a call to
  1456. * FreeRTOS_select().
  1457. *
  1458. * @param[in] pxSocket: The socket whose state we are trying to change.
  1459. * @param[in] eTCPState: The state to which we want to change to.
  1460. */
  1461. void vTCPStateChange( FreeRTOS_Socket_t * pxSocket,
  1462. enum eTCP_STATE eTCPState )
  1463. {
  1464. FreeRTOS_Socket_t * xParent = NULL;
  1465. BaseType_t bBefore = ipNUMERIC_CAST( BaseType_t, tcpNOW_CONNECTED( ( BaseType_t ) pxSocket->u.xTCP.ucTCPState ) ); /* Was it connected ? */
  1466. BaseType_t bAfter = ipNUMERIC_CAST( BaseType_t, tcpNOW_CONNECTED( ( BaseType_t ) eTCPState ) ); /* Is it connected now ? */
  1467. #if ( ipconfigHAS_DEBUG_PRINTF != 0 )
  1468. BaseType_t xPreviousState = ( BaseType_t ) pxSocket->u.xTCP.ucTCPState;
  1469. #endif
  1470. #if ( ipconfigUSE_CALLBACKS == 1 )
  1471. FreeRTOS_Socket_t * xConnected = NULL;
  1472. #endif
  1473. /* Has the connected status changed? */
  1474. if( bBefore != bAfter )
  1475. {
  1476. /* Is the socket connected now ? */
  1477. if( bAfter != pdFALSE )
  1478. {
  1479. /* if bPassQueued is true, this socket is an orphan until it gets connected. */
  1480. if( pxSocket->u.xTCP.bits.bPassQueued != pdFALSE_UNSIGNED )
  1481. {
  1482. /* Now that it is connected, find it's parent. */
  1483. if( pxSocket->u.xTCP.bits.bReuseSocket != pdFALSE_UNSIGNED )
  1484. {
  1485. xParent = pxSocket;
  1486. }
  1487. else
  1488. {
  1489. xParent = pxSocket->u.xTCP.pxPeerSocket;
  1490. configASSERT( xParent != NULL );
  1491. }
  1492. if( xParent != NULL )
  1493. {
  1494. if( xParent->u.xTCP.pxPeerSocket == NULL )
  1495. {
  1496. xParent->u.xTCP.pxPeerSocket = pxSocket;
  1497. }
  1498. xParent->xEventBits |= ( EventBits_t ) eSOCKET_ACCEPT;
  1499. #if ( ipconfigSUPPORT_SELECT_FUNCTION == 1 )
  1500. {
  1501. /* Library support FreeRTOS_select(). Receiving a new
  1502. * connection is being translated as a READ event. */
  1503. if( ( xParent->xSelectBits & ( ( EventBits_t ) eSELECT_READ ) ) != 0U )
  1504. {
  1505. xParent->xEventBits |= ( ( EventBits_t ) eSELECT_READ ) << SOCKET_EVENT_BIT_COUNT;
  1506. }
  1507. }
  1508. #endif
  1509. #if ( ipconfigUSE_CALLBACKS == 1 )
  1510. {
  1511. if( ( ipconfigIS_VALID_PROG_ADDRESS( xParent->u.xTCP.pxHandleConnected ) ) &&
  1512. ( xParent->u.xTCP.bits.bReuseSocket == pdFALSE_UNSIGNED ) )
  1513. {
  1514. /* The listening socket does not become connected itself, in stead
  1515. * a child socket is created.
  1516. * Postpone a call the OnConnect event until the end of this function. */
  1517. xConnected = xParent;
  1518. }
  1519. }
  1520. #endif
  1521. }
  1522. /* Don't need to access the parent socket anymore, so the
  1523. * reference 'pxPeerSocket' may be cleared. */
  1524. pxSocket->u.xTCP.pxPeerSocket = NULL;
  1525. pxSocket->u.xTCP.bits.bPassQueued = pdFALSE_UNSIGNED;
  1526. /* When true, this socket may be returned in a call to accept(). */
  1527. pxSocket->u.xTCP.bits.bPassAccept = pdTRUE_UNSIGNED;
  1528. }
  1529. else
  1530. {
  1531. pxSocket->xEventBits |= ( EventBits_t ) eSOCKET_CONNECT;
  1532. #if ( ipconfigSUPPORT_SELECT_FUNCTION == 1 )
  1533. {
  1534. if( ( pxSocket->xSelectBits & ( ( EventBits_t ) eSELECT_WRITE ) ) != 0U )
  1535. {
  1536. pxSocket->xEventBits |= ( ( EventBits_t ) eSELECT_WRITE ) << SOCKET_EVENT_BIT_COUNT;
  1537. }
  1538. }
  1539. #endif
  1540. }
  1541. }
  1542. else /* bAfter == pdFALSE, connection is closed. */
  1543. {
  1544. /* Notify/wake-up the socket-owner by setting a semaphore. */
  1545. pxSocket->xEventBits |= ( EventBits_t ) eSOCKET_CLOSED;
  1546. #if ( ipconfigSUPPORT_SELECT_FUNCTION == 1 )
  1547. {
  1548. if( ( pxSocket->xSelectBits & ( EventBits_t ) eSELECT_EXCEPT ) != 0U )
  1549. {
  1550. pxSocket->xEventBits |= ( ( EventBits_t ) eSELECT_EXCEPT ) << SOCKET_EVENT_BIT_COUNT;
  1551. }
  1552. }
  1553. #endif
  1554. }
  1555. #if ( ipconfigUSE_CALLBACKS == 1 )
  1556. {
  1557. if( ( ipconfigIS_VALID_PROG_ADDRESS( pxSocket->u.xTCP.pxHandleConnected ) ) && ( xConnected == NULL ) )
  1558. {
  1559. /* The 'connected' state has changed, call the user handler. */
  1560. xConnected = pxSocket;
  1561. }
  1562. }
  1563. #endif /* ipconfigUSE_CALLBACKS */
  1564. if( prvTCPSocketIsActive( ipNUMERIC_CAST( eIPTCPState_t, pxSocket->u.xTCP.ucTCPState ) ) == 0 )
  1565. {
  1566. /* Now the socket isn't in an active state anymore so it
  1567. * won't need further attention of the IP-task.
  1568. * Setting time-out to zero means that the socket won't get checked during
  1569. * timer events. */
  1570. pxSocket->u.xTCP.usTimeout = 0U;
  1571. }
  1572. }
  1573. else
  1574. {
  1575. if( ( eTCPState == eCLOSED ) ||
  1576. ( eTCPState == eCLOSE_WAIT ) )
  1577. {
  1578. /* Socket goes to status eCLOSED because of a RST.
  1579. * When nobody owns the socket yet, delete it. */
  1580. if( ( pxSocket->u.xTCP.bits.bPassQueued != pdFALSE_UNSIGNED ) ||
  1581. ( pxSocket->u.xTCP.bits.bPassAccept != pdFALSE_UNSIGNED ) )
  1582. {
  1583. FreeRTOS_debug_printf( ( "vTCPStateChange: Closing socket\n" ) );
  1584. if( pxSocket->u.xTCP.bits.bReuseSocket == pdFALSE_UNSIGNED )
  1585. {
  1586. ( void ) FreeRTOS_closesocket( pxSocket );
  1587. }
  1588. }
  1589. }
  1590. }
  1591. /* Fill in the new state. */
  1592. pxSocket->u.xTCP.ucTCPState = ( uint8_t ) eTCPState;
  1593. /* Touch the alive timers because moving to another state. */
  1594. prvTCPTouchSocket( pxSocket );
  1595. #if ( ipconfigHAS_DEBUG_PRINTF == 1 )
  1596. {
  1597. if( ( xTCPWindowLoggingLevel >= 0 ) && ( ipconfigTCP_MAY_LOG_PORT( pxSocket->usLocalPort ) ) )
  1598. {
  1599. FreeRTOS_debug_printf( ( "Socket %d -> %lxip:%u State %s->%s\n",
  1600. pxSocket->usLocalPort,
  1601. pxSocket->u.xTCP.ulRemoteIP,
  1602. pxSocket->u.xTCP.usRemotePort,
  1603. FreeRTOS_GetTCPStateName( ( UBaseType_t ) xPreviousState ),
  1604. FreeRTOS_GetTCPStateName( ( UBaseType_t ) eTCPState ) ) );
  1605. }
  1606. }
  1607. #endif /* ipconfigHAS_DEBUG_PRINTF */
  1608. #if ( ipconfigUSE_CALLBACKS == 1 )
  1609. {
  1610. if( xConnected != NULL )
  1611. {
  1612. /* The 'connected' state has changed, call the OnConnect handler of the parent. */
  1613. xConnected->u.xTCP.pxHandleConnected( ( Socket_t ) xConnected, bAfter );
  1614. }
  1615. }
  1616. #endif
  1617. if( xParent != NULL )
  1618. {
  1619. vSocketWakeUpUser( xParent );
  1620. }
  1621. }
  1622. /*-----------------------------------------------------------*/
  1623. /**
  1624. * @brief Check if the size of a network buffer is big enough to hold the outgoing message.
  1625. * Allocate a new bigger network buffer when necessary.
  1626. *
  1627. * @param[in] pxSocket: Socket whose buffer is being resized.
  1628. * @param[in] pxNetworkBuffer: The network buffer whose size is being increased.
  1629. * @param[in] lDataLen: Length of the data to be put in the buffer.
  1630. * @param[in] uxOptionsLength: Length of options.
  1631. *
  1632. * @return If the resizing is successful: The new buffer with the size being asked for
  1633. * with old data copied in it.
  1634. * Else, NULL.
  1635. *
  1636. * @note The old network buffer will be released if the resizing is successful and
  1637. * cannot be used any longer.
  1638. */
  1639. static NetworkBufferDescriptor_t * prvTCPBufferResize( const FreeRTOS_Socket_t * pxSocket,
  1640. NetworkBufferDescriptor_t * pxNetworkBuffer,
  1641. int32_t lDataLen,
  1642. UBaseType_t uxOptionsLength )
  1643. {
  1644. NetworkBufferDescriptor_t * pxReturn;
  1645. size_t uxNeeded;
  1646. BaseType_t xResize;
  1647. if( xBufferAllocFixedSize != pdFALSE )
  1648. {
  1649. /* Network buffers are created with a fixed size and can hold the largest
  1650. * MTU. */
  1651. uxNeeded = ( size_t ) ipTOTAL_ETHERNET_FRAME_SIZE;
  1652. /* and therefore, the buffer won't be too small.
  1653. * Only ask for a new network buffer in case none was supplied. */
  1654. if( pxNetworkBuffer == NULL )
  1655. {
  1656. xResize = pdTRUE;
  1657. }
  1658. else
  1659. {
  1660. xResize = pdFALSE;
  1661. }
  1662. }
  1663. else
  1664. {
  1665. /* Network buffers are created with a variable size. See if it must
  1666. * grow. */
  1667. uxNeeded = ipNUMERIC_CAST( size_t, ipSIZE_OF_ETH_HEADER + uxIPHeaderSizeSocket( pxSocket ) + ipSIZE_OF_TCP_HEADER + uxOptionsLength ) + lDataLen;
  1668. if( uxNeeded < sizeof( pxSocket->u.xTCP.xPacket.u.ucLastPacket ) )
  1669. {
  1670. uxNeeded = sizeof( pxSocket->u.xTCP.xPacket.u.ucLastPacket );
  1671. }
  1672. /* In case we were called from a TCP timer event, a buffer must be
  1673. * created. Otherwise, test 'xDataLength' of the provided buffer. */
  1674. if( ( pxNetworkBuffer == NULL ) || ( pxNetworkBuffer->xDataLength < uxNeeded ) )
  1675. {
  1676. xResize = pdTRUE;
  1677. }
  1678. else
  1679. {
  1680. xResize = pdFALSE;
  1681. }
  1682. }
  1683. if( xResize != pdFALSE )
  1684. {
  1685. /* The caller didn't provide a network buffer or the provided buffer is
  1686. * too small. As we must send-out a data packet, a buffer will be created
  1687. * here. */
  1688. pxReturn = pxGetNetworkBufferWithDescriptor( uxNeeded, 0U );
  1689. if( pxReturn != NULL )
  1690. {
  1691. /* Set the actual packet size, in case the returned buffer is larger. */
  1692. pxReturn->xDataLength = uxNeeded;
  1693. /* Copy the existing data to the new created buffer. */
  1694. if( pxNetworkBuffer != NULL )
  1695. {
  1696. /* Either from the previous buffer... */
  1697. ( void ) memcpy( pxReturn->pucEthernetBuffer, pxNetworkBuffer->pucEthernetBuffer, pxNetworkBuffer->xDataLength );
  1698. /* ...and release it. */
  1699. vReleaseNetworkBufferAndDescriptor( pxNetworkBuffer );
  1700. }
  1701. else
  1702. {
  1703. /* Or from the socket field 'xTCP.xPacket'. */
  1704. ( void ) memcpy( pxReturn->pucEthernetBuffer, pxSocket->u.xTCP.xPacket.u.ucLastPacket, sizeof( pxSocket->u.xTCP.xPacket.u.ucLastPacket ) );
  1705. }
  1706. }
  1707. }
  1708. else
  1709. {
  1710. /* xResize is false, the network buffer provided was big enough. */
  1711. configASSERT( pxNetworkBuffer != NULL ); /* to tell lint: when xResize is false, pxNetworkBuffer is not NULL. */
  1712. pxReturn = pxNetworkBuffer;
  1713. pxNetworkBuffer->xDataLength = ( size_t ) ( ipSIZE_OF_ETH_HEADER + uxIPHeaderSizeSocket( pxSocket ) + ipSIZE_OF_TCP_HEADER + uxOptionsLength ) + ( size_t ) lDataLen;
  1714. }
  1715. return pxReturn;
  1716. }
  1717. /*-----------------------------------------------------------*/
  1718. /**
  1719. * @brief Prepare an outgoing message, in case anything has to be sent.
  1720. *
  1721. * @param[in] pxSocket: The socket owning the connection.
  1722. * @param[in,out] ppxNetworkBuffer: Pointer to the pointer to the network buffer.
  1723. * @param[in] uxOptionsLength: The length of the TCP options.
  1724. *
  1725. * @return Length of the data to be sent if everything is correct. Else, -1
  1726. * is returned in case of any error.
  1727. */
  1728. static int32_t prvTCPPrepareSend( FreeRTOS_Socket_t * pxSocket,
  1729. NetworkBufferDescriptor_t ** ppxNetworkBuffer,
  1730. UBaseType_t uxOptionsLength )
  1731. {
  1732. int32_t lDataLen;
  1733. uint8_t * pucEthernetBuffer, * pucSendData;
  1734. ProtocolHeaders_t * pxProtocolHeaders;
  1735. size_t uxOffset;
  1736. uint32_t ulDataGot, ulDistance;
  1737. TCPWindow_t * pxTCPWindow;
  1738. NetworkBufferDescriptor_t * pxNewBuffer;
  1739. int32_t lStreamPos;
  1740. UBaseType_t uxIntermediateResult = 0;
  1741. if( ( *ppxNetworkBuffer ) != NULL )
  1742. {
  1743. /* A network buffer descriptor was already supplied */
  1744. pucEthernetBuffer = ( *ppxNetworkBuffer )->pucEthernetBuffer;
  1745. }
  1746. else
  1747. {
  1748. /* For now let it point to the last packet header */
  1749. pucEthernetBuffer = pxSocket->u.xTCP.xPacket.u.ucLastPacket;
  1750. }
  1751. /* Map the ethernet buffer onto the ProtocolHeader_t struct for easy access to the fields. */
  1752. pxProtocolHeaders = ipCAST_PTR_TO_TYPE_PTR( ProtocolHeaders_t, &( pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER + uxIPHeaderSizeSocket( pxSocket ) ] ) );
  1753. pxTCPWindow = &( pxSocket->u.xTCP.xTCPWindow );
  1754. lDataLen = 0;
  1755. lStreamPos = 0;
  1756. pxProtocolHeaders->xTCPHeader.ucTCPFlags |= tcpTCP_FLAG_ACK;
  1757. if( pxSocket->u.xTCP.txStream != NULL )
  1758. {
  1759. /* ulTCPWindowTxGet will return the amount of data which may be sent
  1760. * along with the position in the txStream.
  1761. * Why check for MSS > 1 ?
  1762. * Because some TCP-stacks (like uIP) use it for flow-control. */
  1763. if( pxSocket->u.xTCP.usCurMSS > 1U )
  1764. {
  1765. lDataLen = ( int32_t ) ulTCPWindowTxGet( pxTCPWindow, pxSocket->u.xTCP.ulWindowSize, &lStreamPos );
  1766. }
  1767. if( lDataLen > 0 )
  1768. {
  1769. /* Check if the current network buffer is big enough, if not,
  1770. * resize it. */
  1771. pxNewBuffer = prvTCPBufferResize( pxSocket, *ppxNetworkBuffer, lDataLen, uxOptionsLength );
  1772. if( pxNewBuffer != NULL )
  1773. {
  1774. *ppxNetworkBuffer = pxNewBuffer;
  1775. pucEthernetBuffer = pxNewBuffer->pucEthernetBuffer;
  1776. /* Map the byte stream onto ProtocolHeaders_t struct for easy
  1777. * access to the fields. */
  1778. pxProtocolHeaders = ipCAST_PTR_TO_TYPE_PTR( ProtocolHeaders_t, &( pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER + uxIPHeaderSizeSocket( pxSocket ) ] ) );
  1779. pucSendData = &( pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER + uxIPHeaderSizeSocket( pxSocket ) + ipSIZE_OF_TCP_HEADER + uxOptionsLength ] );
  1780. /* Translate the position in txStream to an offset from the tail
  1781. * marker. */
  1782. uxOffset = uxStreamBufferDistance( pxSocket->u.xTCP.txStream, pxSocket->u.xTCP.txStream->uxTail, ( size_t ) lStreamPos );
  1783. /* Here data is copied from the txStream in 'peek' mode. Only
  1784. * when the packets are acked, the tail marker will be updated. */
  1785. ulDataGot = ( uint32_t ) uxStreamBufferGet( pxSocket->u.xTCP.txStream, uxOffset, pucSendData, ( size_t ) lDataLen, pdTRUE );
  1786. #if ( ipconfigHAS_DEBUG_PRINTF != 0 )
  1787. {
  1788. if( ulDataGot != ( uint32_t ) lDataLen )
  1789. {
  1790. FreeRTOS_debug_printf( ( "uxStreamBufferGet: pos %d offs %u only %u != %d\n",
  1791. ( int ) lStreamPos, ( unsigned ) uxOffset, ( unsigned ) ulDataGot, ( int ) lDataLen ) );
  1792. }
  1793. }
  1794. #endif
  1795. /* If the owner of the socket requests a closure, add the FIN
  1796. * flag to the last packet. */
  1797. if( ( pxSocket->u.xTCP.bits.bCloseRequested != pdFALSE_UNSIGNED ) && ( pxSocket->u.xTCP.bits.bFinSent == pdFALSE_UNSIGNED ) )
  1798. {
  1799. ulDistance = ( uint32_t ) uxStreamBufferDistance( pxSocket->u.xTCP.txStream, ( size_t ) lStreamPos, pxSocket->u.xTCP.txStream->uxHead );
  1800. if( ulDistance == ulDataGot )
  1801. {
  1802. #if ( ipconfigHAS_DEBUG_PRINTF == 1 )
  1803. {
  1804. /* the order of volatile accesses is undefined
  1805. * so such workaround */
  1806. size_t uxHead = pxSocket->u.xTCP.txStream->uxHead;
  1807. size_t uxMid = pxSocket->u.xTCP.txStream->uxMid;
  1808. size_t uxTail = pxSocket->u.xTCP.txStream->uxTail;
  1809. FreeRTOS_debug_printf( ( "CheckClose %u <= %u (%u <= %u <= %u)\n",
  1810. ( unsigned ) ulDataGot, ( unsigned ) ulDistance,
  1811. ( unsigned ) uxTail, ( unsigned ) uxMid, ( unsigned ) uxHead ) );
  1812. }
  1813. #endif /* if ( ipconfigHAS_DEBUG_PRINTF == 1 ) */
  1814. /* Although the socket sends a FIN, it will stay in
  1815. * ESTABLISHED until all current data has been received or
  1816. * delivered. */
  1817. pxProtocolHeaders->xTCPHeader.ucTCPFlags |= tcpTCP_FLAG_FIN;
  1818. pxTCPWindow->tx.ulFINSequenceNumber = pxTCPWindow->ulOurSequenceNumber + ( uint32_t ) lDataLen;
  1819. pxSocket->u.xTCP.bits.bFinSent = pdTRUE_UNSIGNED;
  1820. }
  1821. }
  1822. }
  1823. else
  1824. {
  1825. lDataLen = -1;
  1826. }
  1827. }
  1828. }
  1829. if( ( lDataLen >= 0 ) && ( pxSocket->u.xTCP.ucTCPState == ( uint8_t ) eESTABLISHED ) )
  1830. {
  1831. /* See if the socket owner wants to shutdown this connection. */
  1832. if( ( pxSocket->u.xTCP.bits.bUserShutdown != pdFALSE_UNSIGNED ) &&
  1833. ( xTCPWindowTxDone( pxTCPWindow ) != pdFALSE ) )
  1834. {
  1835. pxSocket->u.xTCP.bits.bUserShutdown = pdFALSE_UNSIGNED;
  1836. pxProtocolHeaders->xTCPHeader.ucTCPFlags |= tcpTCP_FLAG_FIN;
  1837. pxSocket->u.xTCP.bits.bFinSent = pdTRUE_UNSIGNED;
  1838. pxSocket->u.xTCP.bits.bWinChange = pdTRUE_UNSIGNED;
  1839. pxTCPWindow->tx.ulFINSequenceNumber = pxTCPWindow->tx.ulCurrentSequenceNumber;
  1840. vTCPStateChange( pxSocket, eFIN_WAIT_1 );
  1841. }
  1842. #if ( ipconfigTCP_KEEP_ALIVE != 0 )
  1843. {
  1844. if( pxSocket->u.xTCP.ucKeepRepCount > 3U ) /*_RB_ Magic number. */
  1845. {
  1846. FreeRTOS_debug_printf( ( "keep-alive: giving up %lxip:%u\n",
  1847. pxSocket->u.xTCP.ulRemoteIP, /* IP address of remote machine. */
  1848. pxSocket->u.xTCP.usRemotePort ) ); /* Port on remote machine. */
  1849. vTCPStateChange( pxSocket, eCLOSE_WAIT );
  1850. lDataLen = -1;
  1851. }
  1852. if( ( lDataLen == 0 ) && ( pxSocket->u.xTCP.bits.bWinChange == pdFALSE_UNSIGNED ) )
  1853. {
  1854. /* If there is no data to be sent, and no window-update message,
  1855. * we might want to send a keep-alive message. */
  1856. TickType_t xAge = xTaskGetTickCount() - pxSocket->u.xTCP.xLastAliveTime;
  1857. TickType_t xMax;
  1858. xMax = ( ( TickType_t ) ipconfigTCP_KEEP_ALIVE_INTERVAL * ( TickType_t ) configTICK_RATE_HZ );
  1859. if( pxSocket->u.xTCP.ucKeepRepCount != ( uint8_t ) 0U )
  1860. {
  1861. xMax = ( TickType_t ) ( 3U * configTICK_RATE_HZ );
  1862. }
  1863. if( xAge > xMax )
  1864. {
  1865. pxSocket->u.xTCP.xLastAliveTime = xTaskGetTickCount();
  1866. if( xTCPWindowLoggingLevel != 0 )
  1867. {
  1868. FreeRTOS_debug_printf( ( "keep-alive: %lxip:%u count %u\n",
  1869. pxSocket->u.xTCP.ulRemoteIP,
  1870. pxSocket->u.xTCP.usRemotePort,
  1871. pxSocket->u.xTCP.ucKeepRepCount ) );
  1872. }
  1873. pxSocket->u.xTCP.bits.bSendKeepAlive = pdTRUE_UNSIGNED;
  1874. pxSocket->u.xTCP.usTimeout = ( ( uint16_t ) pdMS_TO_TICKS( 2500U ) );
  1875. pxSocket->u.xTCP.ucKeepRepCount++;
  1876. }
  1877. }
  1878. }
  1879. #endif /* ipconfigTCP_KEEP_ALIVE */
  1880. }
  1881. /* Anything to send, a change of the advertised window size, or maybe send a
  1882. * keep-alive message? */
  1883. if( ( lDataLen > 0 ) ||
  1884. ( pxSocket->u.xTCP.bits.bWinChange != pdFALSE_UNSIGNED ) ||
  1885. ( pxSocket->u.xTCP.bits.bSendKeepAlive != pdFALSE_UNSIGNED ) )
  1886. {
  1887. pxProtocolHeaders->xTCPHeader.ucTCPFlags &= ( ( uint8_t ) ~tcpTCP_FLAG_PSH );
  1888. pxProtocolHeaders->xTCPHeader.ucTCPOffset = ( uint8_t ) ( ( ipSIZE_OF_TCP_HEADER + uxOptionsLength ) << 2 ); /*_RB_ "2" needs comment. */
  1889. pxProtocolHeaders->xTCPHeader.ucTCPFlags |= ( uint8_t ) tcpTCP_FLAG_ACK;
  1890. if( lDataLen != 0L )
  1891. {
  1892. pxProtocolHeaders->xTCPHeader.ucTCPFlags |= ( uint8_t ) tcpTCP_FLAG_PSH;
  1893. }
  1894. pxProtocolHeaders->xTCPHeader.ucTCPFlags &= ~tcpTCP_FLAG_URG;
  1895. uxIntermediateResult = uxIPHeaderSizeSocket( pxSocket ) + ipSIZE_OF_TCP_HEADER + uxOptionsLength;
  1896. lDataLen += ( int32_t ) uxIntermediateResult;
  1897. }
  1898. return lDataLen;
  1899. }
  1900. /*-----------------------------------------------------------*/
  1901. /**
  1902. * @brief Calculate after how much time this socket needs to be checked again.
  1903. *
  1904. * @param[in] pxSocket: The socket to be checked.
  1905. *
  1906. * @return The number of clock ticks before the timer expires.
  1907. */
  1908. static TickType_t prvTCPNextTimeout( FreeRTOS_Socket_t * pxSocket )
  1909. {
  1910. TickType_t ulDelayMs = ( TickType_t ) tcpMAXIMUM_TCP_WAKEUP_TIME_MS;
  1911. if( pxSocket->u.xTCP.ucTCPState == ( uint8_t ) eCONNECT_SYN )
  1912. {
  1913. /* The socket is actively connecting to a peer. */
  1914. if( pxSocket->u.xTCP.bits.bConnPrepared != pdFALSE_UNSIGNED )
  1915. {
  1916. /* Ethernet address has been found, use progressive timeout for
  1917. * active connect(). */
  1918. if( pxSocket->u.xTCP.ucRepCount < 3U )
  1919. {
  1920. ulDelayMs = ( 3000UL << ( pxSocket->u.xTCP.ucRepCount - 1U ) );
  1921. }
  1922. else
  1923. {
  1924. ulDelayMs = 11000UL;
  1925. }
  1926. }
  1927. else
  1928. {
  1929. /* Still in the ARP phase: check every half second. */
  1930. ulDelayMs = 500UL;
  1931. }
  1932. FreeRTOS_debug_printf( ( "Connect[%lxip:%u]: next timeout %u: %lu ms\n",
  1933. pxSocket->u.xTCP.ulRemoteIP, pxSocket->u.xTCP.usRemotePort,
  1934. pxSocket->u.xTCP.ucRepCount, ulDelayMs ) );
  1935. pxSocket->u.xTCP.usTimeout = ( uint16_t ) ipMS_TO_MIN_TICKS( ulDelayMs );
  1936. }
  1937. else if( pxSocket->u.xTCP.usTimeout == 0U )
  1938. {
  1939. /* Let the sliding window mechanism decide what time-out is appropriate. */
  1940. BaseType_t xResult = xTCPWindowTxHasData( &pxSocket->u.xTCP.xTCPWindow, pxSocket->u.xTCP.ulWindowSize, &ulDelayMs );
  1941. if( ulDelayMs == 0U )
  1942. {
  1943. if( xResult != ( BaseType_t ) 0 )
  1944. {
  1945. ulDelayMs = 1UL;
  1946. }
  1947. else
  1948. {
  1949. ulDelayMs = tcpMAXIMUM_TCP_WAKEUP_TIME_MS;
  1950. }
  1951. }
  1952. else
  1953. {
  1954. /* ulDelayMs contains the time to wait before a re-transmission. */
  1955. }
  1956. pxSocket->u.xTCP.usTimeout = ( uint16_t ) ipMS_TO_MIN_TICKS( ulDelayMs );
  1957. }
  1958. else
  1959. {
  1960. /* field '.usTimeout' has already been set (by the
  1961. * keep-alive/delayed-ACK mechanism). */
  1962. }
  1963. /* Return the number of clock ticks before the timer expires. */
  1964. return ( TickType_t ) pxSocket->u.xTCP.usTimeout;
  1965. }
  1966. /*-----------------------------------------------------------*/
  1967. /**
  1968. * @brief The API FreeRTOS_send() adds data to the TX stream. Add
  1969. * this data to the windowing system to it can be transmitted.
  1970. *
  1971. * @param[in] pxSocket: The socket owning the connection.
  1972. */
  1973. static void prvTCPAddTxData( FreeRTOS_Socket_t * pxSocket )
  1974. {
  1975. int32_t lCount, lLength;
  1976. /* A txStream has been created already, see if the socket has new data for
  1977. * the sliding window.
  1978. *
  1979. * uxStreamBufferMidSpace() returns the distance between rxHead and rxMid. It
  1980. * contains new Tx data which has not been passed to the sliding window yet.
  1981. * The oldest data not-yet-confirmed can be found at rxTail. */
  1982. lLength = ( int32_t ) uxStreamBufferMidSpace( pxSocket->u.xTCP.txStream );
  1983. if( lLength > 0 )
  1984. {
  1985. /* All data between txMid and rxHead will now be passed to the sliding
  1986. * window manager, so it can start transmitting them.
  1987. *
  1988. * Hand over the new data to the sliding window handler. It will be
  1989. * split-up in chunks of 1460 bytes each (or less, depending on
  1990. * ipconfigTCP_MSS). */
  1991. lCount = lTCPWindowTxAdd( &pxSocket->u.xTCP.xTCPWindow,
  1992. ( uint32_t ) lLength,
  1993. ( int32_t ) pxSocket->u.xTCP.txStream->uxMid,
  1994. ( int32_t ) pxSocket->u.xTCP.txStream->LENGTH );
  1995. /* Move the rxMid pointer forward up to rxHead. */
  1996. if( lCount > 0 )
  1997. {
  1998. vStreamBufferMoveMid( pxSocket->u.xTCP.txStream, ( size_t ) lCount );
  1999. }
  2000. }
  2001. }
  2002. /*-----------------------------------------------------------*/
  2003. /**
  2004. * @brief prvTCPHandleFin() will be called to handle connection closure. The
  2005. * closure starts when either a FIN has been received and accepted,
  2006. * or when the socket has sent a FIN flag to the peer. Before being
  2007. * called, it has been checked that both reception and transmission
  2008. * are complete.
  2009. *
  2010. * @param[in] pxSocket: Socket owning the the connection.
  2011. * @param[in] pxNetworkBuffer: The network buffer carrying the TCP packet.
  2012. *
  2013. * @return Length of the packet to be sent.
  2014. */
  2015. static BaseType_t prvTCPHandleFin( FreeRTOS_Socket_t * pxSocket,
  2016. const NetworkBufferDescriptor_t * pxNetworkBuffer )
  2017. {
  2018. /* Map the ethernet buffer onto the ProtocolHeader_t struct for easy access to the fields. */
  2019. ProtocolHeaders_t * pxProtocolHeaders = ipCAST_PTR_TO_TYPE_PTR( ProtocolHeaders_t,
  2020. &( pxNetworkBuffer->pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER + xIPHeaderSize( pxNetworkBuffer ) ] ) );
  2021. TCPHeader_t * pxTCPHeader = &( pxProtocolHeaders->xTCPHeader );
  2022. uint8_t ucIntermediateResult = 0, ucTCPFlags = pxTCPHeader->ucTCPFlags;
  2023. TCPWindow_t * pxTCPWindow = &pxSocket->u.xTCP.xTCPWindow;
  2024. BaseType_t xSendLength = 0;
  2025. uint32_t ulAckNr = FreeRTOS_ntohl( pxTCPHeader->ulAckNr );
  2026. if( ( ucTCPFlags & tcpTCP_FLAG_FIN ) != 0U )
  2027. {
  2028. pxTCPWindow->rx.ulCurrentSequenceNumber = pxTCPWindow->rx.ulFINSequenceNumber + 1U;
  2029. }
  2030. if( pxSocket->u.xTCP.bits.bFinSent == pdFALSE_UNSIGNED )
  2031. {
  2032. /* We haven't yet replied with a FIN, do so now. */
  2033. pxTCPWindow->tx.ulFINSequenceNumber = pxTCPWindow->tx.ulCurrentSequenceNumber;
  2034. pxSocket->u.xTCP.bits.bFinSent = pdTRUE_UNSIGNED;
  2035. }
  2036. else
  2037. {
  2038. /* We did send a FIN already, see if it's ACK'd. */
  2039. if( ulAckNr == ( pxTCPWindow->tx.ulFINSequenceNumber + 1UL ) )
  2040. {
  2041. pxSocket->u.xTCP.bits.bFinAcked = pdTRUE_UNSIGNED;
  2042. }
  2043. }
  2044. if( pxSocket->u.xTCP.bits.bFinAcked == pdFALSE_UNSIGNED )
  2045. {
  2046. pxTCPWindow->tx.ulCurrentSequenceNumber = pxTCPWindow->tx.ulFINSequenceNumber;
  2047. pxTCPHeader->ucTCPFlags = ( uint8_t ) tcpTCP_FLAG_ACK | ( uint8_t ) tcpTCP_FLAG_FIN;
  2048. /* And wait for the final ACK. */
  2049. vTCPStateChange( pxSocket, eLAST_ACK );
  2050. }
  2051. else
  2052. {
  2053. /* Our FIN has been ACK'd, the outgoing sequence number is now fixed. */
  2054. pxTCPWindow->tx.ulCurrentSequenceNumber = pxTCPWindow->tx.ulFINSequenceNumber + 1U;
  2055. if( pxSocket->u.xTCP.bits.bFinRecv == pdFALSE_UNSIGNED )
  2056. {
  2057. /* We have sent out a FIN but the peer hasn't replied with a FIN
  2058. * yet. Do nothing for the moment. */
  2059. pxTCPHeader->ucTCPFlags = 0U;
  2060. }
  2061. else
  2062. {
  2063. if( pxSocket->u.xTCP.bits.bFinLast == pdFALSE_UNSIGNED )
  2064. {
  2065. /* This is the third of the three-way hand shake: the last
  2066. * ACK. */
  2067. pxTCPHeader->ucTCPFlags = tcpTCP_FLAG_ACK;
  2068. }
  2069. else
  2070. {
  2071. /* The other party started the closure, so we just wait for the
  2072. * last ACK. */
  2073. pxTCPHeader->ucTCPFlags = 0U;
  2074. }
  2075. /* And wait for the user to close this socket. */
  2076. vTCPStateChange( pxSocket, eCLOSE_WAIT );
  2077. }
  2078. }
  2079. pxTCPWindow->ulOurSequenceNumber = pxTCPWindow->tx.ulCurrentSequenceNumber;
  2080. if( pxTCPHeader->ucTCPFlags != 0U )
  2081. {
  2082. ucIntermediateResult = uxIPHeaderSizeSocket( pxSocket ) + ipSIZE_OF_TCP_HEADER + pxTCPWindow->ucOptionLength;
  2083. xSendLength = ( BaseType_t ) ucIntermediateResult;
  2084. }
  2085. pxTCPHeader->ucTCPOffset = ( uint8_t ) ( ( ipSIZE_OF_TCP_HEADER + pxTCPWindow->ucOptionLength ) << 2 );
  2086. if( xTCPWindowLoggingLevel != 0 )
  2087. {
  2088. FreeRTOS_debug_printf( ( "TCP: send FIN+ACK (ack %lu, cur/nxt %lu/%lu) ourSeqNr %lu | Rx %lu\n",
  2089. ulAckNr - pxTCPWindow->tx.ulFirstSequenceNumber,
  2090. pxTCPWindow->tx.ulCurrentSequenceNumber - pxTCPWindow->tx.ulFirstSequenceNumber,
  2091. pxTCPWindow->ulNextTxSequenceNumber - pxTCPWindow->tx.ulFirstSequenceNumber,
  2092. pxTCPWindow->ulOurSequenceNumber - pxTCPWindow->tx.ulFirstSequenceNumber,
  2093. pxTCPWindow->rx.ulCurrentSequenceNumber - pxTCPWindow->rx.ulFirstSequenceNumber ) );
  2094. }
  2095. return xSendLength;
  2096. }
  2097. /*-----------------------------------------------------------*/
  2098. /**
  2099. * @brief prvCheckRxData(): called from prvTCPHandleState(). The
  2100. * first thing that will be done is find the TCP payload data
  2101. * and check the length of this data.
  2102. *
  2103. * @param[in] pxNetworkBuffer: The network buffer holding the received data.
  2104. * @param[out] ppucRecvData: It will point to first byte of the TCP payload.
  2105. *
  2106. * @return Length of the received buffer.
  2107. */
  2108. static BaseType_t prvCheckRxData( const NetworkBufferDescriptor_t * pxNetworkBuffer,
  2109. uint8_t ** ppucRecvData )
  2110. {
  2111. /* Map the ethernet buffer onto the ProtocolHeader_t struct for easy access to the fields. */
  2112. const ProtocolHeaders_t * pxProtocolHeaders = ipCAST_PTR_TO_TYPE_PTR( ProtocolHeaders_t,
  2113. &( pxNetworkBuffer->pucEthernetBuffer[ ( size_t ) ipSIZE_OF_ETH_HEADER + xIPHeaderSize( pxNetworkBuffer ) ] ) );
  2114. const TCPHeader_t * pxTCPHeader = &( pxProtocolHeaders->xTCPHeader );
  2115. int32_t lLength, lTCPHeaderLength, lReceiveLength; //lUrgentLength;
  2116. /* Map the buffer onto an IPHeader_t struct for easy access to fields. */
  2117. const IPHeader_t * pxIPHeader = ipCAST_CONST_PTR_TO_CONST_TYPE_PTR( IPHeader_t, &( pxNetworkBuffer->pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER ] ) );
  2118. const size_t xIPHeaderLength = ipSIZE_OF_IPv4_HEADER;
  2119. uint16_t usLength;
  2120. uint8_t ucIntermediateResult = 0;
  2121. /* Determine the length and the offset of the user-data sent to this
  2122. * node.
  2123. *
  2124. * The size of the TCP header is given in a multiple of 4-byte words (single
  2125. * byte, needs no ntoh() translation). A shift-right 2: is the same as
  2126. * (offset >> 4) * 4. */
  2127. ucIntermediateResult = ( pxTCPHeader->ucTCPOffset & tcpVALID_BITS_IN_TCP_OFFSET_BYTE ) >> 2;
  2128. lTCPHeaderLength = ( int32_t ) ucIntermediateResult;
  2129. /* Let pucRecvData point to the first byte received. */
  2130. *ppucRecvData = &( pxNetworkBuffer->pucEthernetBuffer[ ( size_t ) ipSIZE_OF_ETH_HEADER + xIPHeaderLength + ( size_t ) lTCPHeaderLength ] );
  2131. /* Calculate lReceiveLength - the length of the TCP data received. This is
  2132. * equal to the total packet length minus:
  2133. * ( LinkLayer length (14) + IP header length (20) + size of TCP header(20 +) ).*/
  2134. lReceiveLength = ipNUMERIC_CAST( int32_t, pxNetworkBuffer->xDataLength ) - ( int32_t ) ipSIZE_OF_ETH_HEADER;
  2135. usLength = FreeRTOS_htons( pxIPHeader->usLength );
  2136. lLength = ( int32_t ) usLength;
  2137. if( lReceiveLength > lLength )
  2138. {
  2139. /* More bytes were received than the reported length, often because of
  2140. * padding bytes at the end. */
  2141. lReceiveLength = lLength;
  2142. }
  2143. /* Subtract the size of the TCP and IP headers and the actual data size is
  2144. * known. */
  2145. if( lReceiveLength > ( lTCPHeaderLength + ( int32_t ) xIPHeaderLength ) )
  2146. {
  2147. lReceiveLength -= ( lTCPHeaderLength + ( int32_t ) xIPHeaderLength );
  2148. }
  2149. else
  2150. {
  2151. lReceiveLength = 0;
  2152. }
  2153. /* Urgent Pointer:
  2154. * This field communicates the current value of the urgent pointer as a
  2155. * positive offset from the sequence number in this segment. The urgent
  2156. * pointer points to the sequence number of the octet following the urgent
  2157. * data. This field is only be interpreted in segments with the URG control
  2158. * bit set. */
  2159. if( ( pxTCPHeader->ucTCPFlags & tcpTCP_FLAG_URG ) != 0U )
  2160. {
  2161. /* Although we ignore the urgent data, we have to skip it. */
  2162. /* lUrgentLength = ( int32_t ) FreeRTOS_htons( pxTCPHeader->usUrgent );
  2163. *ppucRecvData += lUrgentLength;
  2164. lReceiveLength -= FreeRTOS_min_int32( lReceiveLength, lUrgentLength ); */
  2165. }
  2166. return ( BaseType_t ) lReceiveLength;
  2167. }
  2168. /*-----------------------------------------------------------*/
  2169. /**
  2170. * @brief prvStoreRxData(): called from prvTCPHandleState().
  2171. * The second thing is to do is check if the payload data may
  2172. * be accepted. If so, they will be added to the reception queue.
  2173. *
  2174. * @param[in] pxSocket: The socket owning the connection.
  2175. * @param[in] pucRecvData: Pointer to received data.
  2176. * @param[in] pxNetworkBuffer: The network buffer descriptor.
  2177. * @param[in] ulReceiveLength: The length of the received data.
  2178. *
  2179. * @return 0 on success, -1 on failure of storing data.
  2180. */
  2181. static BaseType_t prvStoreRxData( FreeRTOS_Socket_t * pxSocket,
  2182. const uint8_t * pucRecvData,
  2183. NetworkBufferDescriptor_t * pxNetworkBuffer,
  2184. uint32_t ulReceiveLength )
  2185. {
  2186. /* Map the ethernet buffer onto the ProtocolHeader_t struct for easy access to the fields. */
  2187. const ProtocolHeaders_t * pxProtocolHeaders = ipCAST_CONST_PTR_TO_CONST_TYPE_PTR( ProtocolHeaders_t,
  2188. &( pxNetworkBuffer->pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER + xIPHeaderSize( pxNetworkBuffer ) ] ) );
  2189. const TCPHeader_t * pxTCPHeader = &pxProtocolHeaders->xTCPHeader;
  2190. TCPWindow_t * pxTCPWindow = &pxSocket->u.xTCP.xTCPWindow;
  2191. uint32_t ulSequenceNumber, ulSpace;
  2192. int32_t lOffset, lStored;
  2193. BaseType_t xResult = 0;
  2194. ulSequenceNumber = FreeRTOS_ntohl( pxTCPHeader->ulSequenceNumber );
  2195. if( ( ulReceiveLength > 0U ) && ( pxSocket->u.xTCP.ucTCPState >= ( uint8_t ) eSYN_RECEIVED ) )
  2196. {
  2197. /* See if way may accept the data contents and forward it to the socket
  2198. * owner.
  2199. *
  2200. * If it can't be "accept"ed it may have to be stored and send a selective
  2201. * ack (SACK) option to confirm it. In that case, lTCPAddRxdata() will be
  2202. * called later to store an out-of-order packet (in case lOffset is
  2203. * negative). */
  2204. if( pxSocket->u.xTCP.rxStream != NULL )
  2205. {
  2206. ulSpace = ( uint32_t ) uxStreamBufferGetSpace( pxSocket->u.xTCP.rxStream );
  2207. }
  2208. else
  2209. {
  2210. ulSpace = ( uint32_t ) pxSocket->u.xTCP.uxRxStreamSize;
  2211. }
  2212. lOffset = lTCPWindowRxCheck( pxTCPWindow, ulSequenceNumber, ulReceiveLength, ulSpace );
  2213. if( lOffset >= 0 )
  2214. {
  2215. /* New data has arrived and may be made available to the user. See
  2216. * if the head marker in rxStream may be advanced, only if lOffset == 0.
  2217. * In case the low-water mark is reached, bLowWater will be set
  2218. * "low-water" here stands for "little space". */
  2219. lStored = lTCPAddRxdata( pxSocket, ( uint32_t ) lOffset, pucRecvData, ulReceiveLength );
  2220. if( lStored != ( int32_t ) ulReceiveLength )
  2221. {
  2222. FreeRTOS_debug_printf( ( "lTCPAddRxdata: stored %ld / %lu bytes? ?\n", lStored, ulReceiveLength ) );
  2223. /* Received data could not be stored. The socket's flag
  2224. * bMallocError has been set. The socket now has the status
  2225. * eCLOSE_WAIT and a RST packet will be sent back. */
  2226. ( void ) prvTCPSendReset( pxNetworkBuffer );
  2227. xResult = -1;
  2228. }
  2229. }
  2230. /* After a missing packet has come in, higher packets may be passed to
  2231. * the user. */
  2232. #if ( ipconfigUSE_TCP_WIN == 1 )
  2233. {
  2234. /* Now lTCPAddRxdata() will move the rxHead pointer forward
  2235. * so data becomes available to the user immediately
  2236. * In case the low-water mark is reached, bLowWater will be set. */
  2237. if( ( xResult == 0 ) && ( pxTCPWindow->ulUserDataLength > 0UL ) )
  2238. {
  2239. ( void ) lTCPAddRxdata( pxSocket, 0UL, NULL, pxTCPWindow->ulUserDataLength );
  2240. pxTCPWindow->ulUserDataLength = 0;
  2241. }
  2242. }
  2243. #endif /* ipconfigUSE_TCP_WIN */
  2244. }
  2245. else
  2246. {
  2247. pxTCPWindow->ucOptionLength = 0U;
  2248. }
  2249. return xResult;
  2250. }
  2251. /*-----------------------------------------------------------*/
  2252. /**
  2253. * @brief Set the TCP options (if any) for the outgoing packet.
  2254. *
  2255. * @param[in] pxSocket: The socket owning the connection.
  2256. * @param[in] pxNetworkBuffer: The network buffer holding the packet.
  2257. *
  2258. * @return Length of the TCP options after they are set.
  2259. */
  2260. static UBaseType_t prvSetOptions( FreeRTOS_Socket_t * pxSocket,
  2261. const NetworkBufferDescriptor_t * pxNetworkBuffer )
  2262. {
  2263. /* Map the ethernet buffer onto the ProtocolHeader_t struct for easy access to the fields. */
  2264. ProtocolHeaders_t * pxProtocolHeaders = ipCAST_PTR_TO_TYPE_PTR( ProtocolHeaders_t,
  2265. &( pxNetworkBuffer->pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER + xIPHeaderSize( pxNetworkBuffer ) ] ) );
  2266. TCPHeader_t * pxTCPHeader = &pxProtocolHeaders->xTCPHeader;
  2267. const TCPWindow_t * pxTCPWindow = &pxSocket->u.xTCP.xTCPWindow;
  2268. UBaseType_t uxOptionsLength = pxTCPWindow->ucOptionLength;
  2269. /* memcpy() helper variables for MISRA Rule 21.15 compliance*/
  2270. const void * pvCopySource;
  2271. void * pvCopyDest;
  2272. #if ( ipconfigUSE_TCP_WIN == 1 )
  2273. if( uxOptionsLength != 0U )
  2274. {
  2275. /* TCP options must be sent because a packet which is out-of-order
  2276. * was received. */
  2277. if( xTCPWindowLoggingLevel >= 0 )
  2278. {
  2279. FreeRTOS_debug_printf( ( "SACK[%d,%d]: optlen %lu sending %lu - %lu\r\n",
  2280. pxSocket->usLocalPort,
  2281. pxSocket->u.xTCP.usRemotePort,
  2282. uxOptionsLength,
  2283. FreeRTOS_ntohl( pxTCPWindow->ulOptionsData[ 1 ] ) - pxSocket->u.xTCP.xTCPWindow.rx.ulFirstSequenceNumber,
  2284. FreeRTOS_ntohl( pxTCPWindow->ulOptionsData[ 2 ] ) - pxSocket->u.xTCP.xTCPWindow.rx.ulFirstSequenceNumber ) );
  2285. }
  2286. /*
  2287. * Use helper variables for memcpy() source & dest to remain
  2288. * compliant with MISRA Rule 21.15. These should be
  2289. * optimized away.
  2290. */
  2291. pvCopySource = pxTCPWindow->ulOptionsData;
  2292. pvCopyDest = pxTCPHeader->ucOptdata;
  2293. ( void ) memcpy( pvCopyDest, pvCopySource, ( size_t ) uxOptionsLength );
  2294. /* The header length divided by 4, goes into the higher nibble,
  2295. * effectively a shift-left 2. */
  2296. pxTCPHeader->ucTCPOffset = ( uint8_t ) ( ( ipSIZE_OF_TCP_HEADER + uxOptionsLength ) << 2 );
  2297. }
  2298. else
  2299. #endif /* ipconfigUSE_TCP_WIN */
  2300. if( ( pxSocket->u.xTCP.ucTCPState >= ( EventBits_t ) eESTABLISHED ) && ( pxSocket->u.xTCP.bits.bMssChange != pdFALSE_UNSIGNED ) )
  2301. {
  2302. /* TCP options must be sent because the MSS has changed. */
  2303. pxSocket->u.xTCP.bits.bMssChange = pdFALSE_UNSIGNED;
  2304. if( xTCPWindowLoggingLevel >= 0 )
  2305. {
  2306. FreeRTOS_debug_printf( ( "MSS: sending %d\n", pxSocket->u.xTCP.usCurMSS ) );
  2307. }
  2308. pxTCPHeader->ucOptdata[ 0 ] = tcpTCP_OPT_MSS;
  2309. pxTCPHeader->ucOptdata[ 1 ] = tcpTCP_OPT_MSS_LEN;
  2310. pxTCPHeader->ucOptdata[ 2 ] = ( uint8_t ) ( ( pxSocket->u.xTCP.usCurMSS ) >> 8 );
  2311. pxTCPHeader->ucOptdata[ 3 ] = ( uint8_t ) ( ( pxSocket->u.xTCP.usCurMSS ) & 0xffU );
  2312. uxOptionsLength = 4U;
  2313. pxTCPHeader->ucTCPOffset = ( uint8_t ) ( ( ipSIZE_OF_TCP_HEADER + uxOptionsLength ) << 2 );
  2314. }
  2315. else
  2316. {
  2317. /* Nothing. */
  2318. }
  2319. return uxOptionsLength;
  2320. }
  2321. /*-----------------------------------------------------------*/
  2322. /**
  2323. * @brief prvHandleSynReceived(): called from prvTCPHandleState(). Called
  2324. * from the states: eSYN_RECEIVED and eCONNECT_SYN. If the flags
  2325. * received are correct, the socket will move to eESTABLISHED.
  2326. *
  2327. * @param[in] pxSocket: The socket handling the connection.
  2328. * @param[in] pxNetworkBuffer: The pointer to the network buffer carrying
  2329. * the packet.
  2330. * @param[in] ulReceiveLength: Length in bytes of the data received.
  2331. * @param[in] uxOptionsLength: Length of the TCP options in bytes.
  2332. *
  2333. * @return Length of the data to be sent.
  2334. */
  2335. static BaseType_t prvHandleSynReceived( FreeRTOS_Socket_t * pxSocket,
  2336. const NetworkBufferDescriptor_t * pxNetworkBuffer,
  2337. uint32_t ulReceiveLength,
  2338. UBaseType_t uxOptionsLength )
  2339. {
  2340. /* Map the ethernet buffer onto the ProtocolHeader_t struct for easy access to the fields. */
  2341. ProtocolHeaders_t * pxProtocolHeaders = ipCAST_PTR_TO_TYPE_PTR( ProtocolHeaders_t,
  2342. &( pxNetworkBuffer->pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER + uxIPHeaderSizeSocket( pxSocket ) ] ) );
  2343. TCPHeader_t * pxTCPHeader = &pxProtocolHeaders->xTCPHeader;
  2344. TCPWindow_t * pxTCPWindow = &pxSocket->u.xTCP.xTCPWindow;
  2345. uint8_t ucTCPFlags = pxTCPHeader->ucTCPFlags;
  2346. uint32_t ulSequenceNumber = FreeRTOS_ntohl( pxTCPHeader->ulSequenceNumber );
  2347. BaseType_t xSendLength = 0;
  2348. UBaseType_t uxIntermediateResult = 0U;
  2349. /* Either expect a ACK or a SYN+ACK. */
  2350. uint8_t ucExpect = tcpTCP_FLAG_ACK;
  2351. const uint8_t ucFlagsMask = tcpTCP_FLAG_ACK | tcpTCP_FLAG_RST | tcpTCP_FLAG_SYN | tcpTCP_FLAG_FIN;
  2352. if( pxSocket->u.xTCP.ucTCPState == ( uint8_t ) eCONNECT_SYN )
  2353. {
  2354. ucExpect |= tcpTCP_FLAG_SYN;
  2355. }
  2356. if( ( ucTCPFlags & ucFlagsMask ) != ucExpect )
  2357. {
  2358. /* eSYN_RECEIVED: flags 0010 expected, not 0002. */
  2359. /* eSYN_RECEIVED: flags ACK expected, not SYN. */
  2360. FreeRTOS_debug_printf( ( "%s: flags %04X expected, not %04X\n",
  2361. ( pxSocket->u.xTCP.ucTCPState == ( uint8_t ) eSYN_RECEIVED ) ? "eSYN_RECEIVED" : "eCONNECT_SYN",
  2362. ucExpect, ucTCPFlags ) );
  2363. /* In case pxSocket is not yet owned by the application, a closure
  2364. * of the socket will be scheduled for the next cycle. */
  2365. vTCPStateChange( pxSocket, eCLOSE_WAIT );
  2366. /* Send RST with the expected sequence and ACK numbers,
  2367. * otherwise the packet will be ignored. */
  2368. pxTCPWindow->ulOurSequenceNumber = FreeRTOS_htonl( pxTCPHeader->ulAckNr );
  2369. pxTCPWindow->rx.ulCurrentSequenceNumber = ulSequenceNumber;
  2370. pxTCPHeader->ucTCPFlags |= tcpTCP_FLAG_RST;
  2371. uxIntermediateResult = uxIPHeaderSizeSocket( pxSocket ) + ipSIZE_OF_TCP_HEADER + uxOptionsLength;
  2372. xSendLength = ( BaseType_t ) uxIntermediateResult;
  2373. pxTCPHeader->ucTCPOffset = ( uint8_t ) ( ( ipSIZE_OF_TCP_HEADER + uxOptionsLength ) << 2 );
  2374. }
  2375. else
  2376. {
  2377. pxTCPWindow->usPeerPortNumber = pxSocket->u.xTCP.usRemotePort;
  2378. pxTCPWindow->usOurPortNumber = pxSocket->usLocalPort;
  2379. if( pxSocket->u.xTCP.ucTCPState == ( uint8_t ) eCONNECT_SYN )
  2380. {
  2381. /* Map the Last packet onto the ProtocolHeader_t struct for easy access to the fields. */
  2382. ProtocolHeaders_t * pxLastHeaders = ipCAST_PTR_TO_TYPE_PTR( ProtocolHeaders_t,
  2383. &( pxSocket->u.xTCP.xPacket.u.ucLastPacket[ ipSIZE_OF_ETH_HEADER + uxIPHeaderSizeSocket( pxSocket ) ] ) );
  2384. /* Clear the SYN flag in lastPacket. */
  2385. pxLastHeaders->xTCPHeader.ucTCPFlags = tcpTCP_FLAG_ACK;
  2386. pxProtocolHeaders->xTCPHeader.ucTCPFlags = tcpTCP_FLAG_ACK;
  2387. /* This socket was the one connecting actively so now perform the
  2388. * synchronisation. */
  2389. vTCPWindowInit( &pxSocket->u.xTCP.xTCPWindow,
  2390. ulSequenceNumber, pxSocket->u.xTCP.xTCPWindow.ulOurSequenceNumber, ( uint32_t ) pxSocket->u.xTCP.usCurMSS );
  2391. pxTCPWindow->rx.ulHighestSequenceNumber = ulSequenceNumber + 1U;
  2392. pxTCPWindow->rx.ulCurrentSequenceNumber = ulSequenceNumber + 1U;
  2393. pxTCPWindow->tx.ulCurrentSequenceNumber++; /* because we send a TCP_SYN [ | TCP_ACK ]; */
  2394. pxTCPWindow->ulNextTxSequenceNumber++;
  2395. }
  2396. else if( ulReceiveLength == 0U )
  2397. {
  2398. pxTCPWindow->rx.ulCurrentSequenceNumber = ulSequenceNumber;
  2399. }
  2400. else
  2401. {
  2402. /* Nothing. */
  2403. }
  2404. /* The SYN+ACK has been confirmed, increase the next sequence number by
  2405. * 1. */
  2406. pxTCPWindow->ulOurSequenceNumber = pxTCPWindow->tx.ulFirstSequenceNumber + 1U;
  2407. #if ( ipconfigUSE_TCP_WIN == 1 )
  2408. {
  2409. FreeRTOS_debug_printf( ( "TCP: %s %d => %lxip:%d set ESTAB (scaling %u)\n",
  2410. ( pxSocket->u.xTCP.ucTCPState == ( uint8_t ) eCONNECT_SYN ) ? "active" : "passive",
  2411. pxSocket->usLocalPort,
  2412. pxSocket->u.xTCP.ulRemoteIP,
  2413. pxSocket->u.xTCP.usRemotePort,
  2414. ( unsigned ) pxSocket->u.xTCP.bits.bWinScaling ) );
  2415. }
  2416. #endif /* ipconfigUSE_TCP_WIN */
  2417. if( ( pxSocket->u.xTCP.ucTCPState == ( EventBits_t ) eCONNECT_SYN ) || ( ulReceiveLength != 0UL ) )
  2418. {
  2419. pxTCPHeader->ucTCPFlags = tcpTCP_FLAG_ACK;
  2420. uxIntermediateResult = uxIPHeaderSizeSocket( pxSocket ) + ( size_t ) ipSIZE_OF_TCP_HEADER + uxOptionsLength;
  2421. xSendLength = ( BaseType_t ) uxIntermediateResult;
  2422. pxTCPHeader->ucTCPOffset = ( uint8_t ) ( ( ipSIZE_OF_TCP_HEADER + uxOptionsLength ) << 2 );
  2423. }
  2424. #if ( ipconfigUSE_TCP_WIN != 0 )
  2425. {
  2426. if( pxSocket->u.xTCP.bits.bWinScaling == pdFALSE_UNSIGNED )
  2427. {
  2428. /* The other party did not send a scaling factor.
  2429. * A shifting factor in this side must be canceled. */
  2430. pxSocket->u.xTCP.ucMyWinScaleFactor = 0;
  2431. pxSocket->u.xTCP.ucPeerWinScaleFactor = 0;
  2432. }
  2433. }
  2434. #endif /* ipconfigUSE_TCP_WIN */
  2435. /* This was the third step of connecting: SYN, SYN+ACK, ACK so now the
  2436. * connection is established. */
  2437. vTCPStateChange( pxSocket, eESTABLISHED );
  2438. }
  2439. return xSendLength;
  2440. }
  2441. /*-----------------------------------------------------------*/
  2442. /**
  2443. * @brief prvHandleEstablished(): called from prvTCPHandleState()
  2444. * Called if the status is eESTABLISHED. Data reception has been handled
  2445. * earlier. Here the ACK's from peer will be checked, and if a FIN is received,
  2446. * the code will check if it may be accepted, i.e. if all expected data has been
  2447. * completely received.
  2448. *
  2449. * @param[in] pxSocket: The socket owning the connection.
  2450. * @param[in,out] ppxNetworkBuffer: Pointer to pointer to the network buffer.
  2451. * @param[in] ulReceiveLength: The length of the received packet.
  2452. * @param[in] uxOptionsLength: Length of TCP options.
  2453. *
  2454. * @return The send length of the packet to be sent.
  2455. */
  2456. static BaseType_t prvHandleEstablished( FreeRTOS_Socket_t * pxSocket,
  2457. NetworkBufferDescriptor_t ** ppxNetworkBuffer,
  2458. uint32_t ulReceiveLength,
  2459. UBaseType_t uxOptionsLength )
  2460. {
  2461. /* Map the buffer onto the ProtocolHeader_t struct for easy access to the fields. */
  2462. ProtocolHeaders_t * pxProtocolHeaders = ipCAST_PTR_TO_TYPE_PTR( ProtocolHeaders_t,
  2463. &( ( *ppxNetworkBuffer )->pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER + uxIPHeaderSizeSocket( pxSocket ) ] ) );
  2464. TCPHeader_t * pxTCPHeader = &pxProtocolHeaders->xTCPHeader;
  2465. TCPWindow_t * pxTCPWindow = &pxSocket->u.xTCP.xTCPWindow;
  2466. uint8_t ucTCPFlags = pxTCPHeader->ucTCPFlags;
  2467. uint32_t ulSequenceNumber = FreeRTOS_ntohl( pxTCPHeader->ulSequenceNumber ), ulCount, ulIntermediateResult = 0;
  2468. BaseType_t xSendLength = 0, xMayClose = pdFALSE, bRxComplete, bTxDone;
  2469. int32_t lDistance, lSendResult;
  2470. uint16_t usWindow;
  2471. UBaseType_t uxIntermediateResult = 0;
  2472. /* Remember the window size the peer is advertising. */
  2473. usWindow = FreeRTOS_ntohs( pxTCPHeader->usWindow );
  2474. pxSocket->u.xTCP.ulWindowSize = ( uint32_t ) usWindow;
  2475. #if ( ipconfigUSE_TCP_WIN != 0 )
  2476. {
  2477. pxSocket->u.xTCP.ulWindowSize =
  2478. ( pxSocket->u.xTCP.ulWindowSize << pxSocket->u.xTCP.ucPeerWinScaleFactor );
  2479. }
  2480. #endif /* ipconfigUSE_TCP_WIN */
  2481. if( ( ucTCPFlags & ( uint8_t ) tcpTCP_FLAG_ACK ) != 0U )
  2482. {
  2483. ulCount = ulTCPWindowTxAck( pxTCPWindow, FreeRTOS_ntohl( pxTCPHeader->ulAckNr ) );
  2484. /* ulTCPWindowTxAck() returns the number of bytes which have been acked,
  2485. * starting at 'tx.ulCurrentSequenceNumber'. Advance the tail pointer in
  2486. * txStream. */
  2487. if( ( pxSocket->u.xTCP.txStream != NULL ) && ( ulCount > 0U ) )
  2488. {
  2489. /* Just advancing the tail index, 'ulCount' bytes have been
  2490. * confirmed, and because there is new space in the txStream, the
  2491. * user/owner should be woken up. */
  2492. /* _HT_ : only in case the socket's waiting? */
  2493. if( uxStreamBufferGet( pxSocket->u.xTCP.txStream, 0U, NULL, ( size_t ) ulCount, pdFALSE ) != 0U )
  2494. {
  2495. pxSocket->xEventBits |= ( EventBits_t ) eSOCKET_SEND;
  2496. #if ipconfigSUPPORT_SELECT_FUNCTION == 1
  2497. {
  2498. if( ( pxSocket->xSelectBits & ( ( EventBits_t ) eSELECT_WRITE ) ) != 0U )
  2499. {
  2500. pxSocket->xEventBits |= ( ( EventBits_t ) eSELECT_WRITE ) << SOCKET_EVENT_BIT_COUNT;
  2501. }
  2502. }
  2503. #endif
  2504. /* In case the socket owner has installed an OnSent handler,
  2505. * call it now. */
  2506. #if ( ipconfigUSE_CALLBACKS == 1 )
  2507. {
  2508. if( ipconfigIS_VALID_PROG_ADDRESS( pxSocket->u.xTCP.pxHandleSent ) )
  2509. {
  2510. pxSocket->u.xTCP.pxHandleSent( ( Socket_t ) pxSocket, ulCount );
  2511. }
  2512. }
  2513. #endif /* ipconfigUSE_CALLBACKS == 1 */
  2514. }
  2515. }
  2516. }
  2517. /* If this socket has a stream for transmission, add the data to the
  2518. * outgoing segment(s). */
  2519. if( pxSocket->u.xTCP.txStream != NULL )
  2520. {
  2521. prvTCPAddTxData( pxSocket );
  2522. }
  2523. pxSocket->u.xTCP.xTCPWindow.ulOurSequenceNumber = pxTCPWindow->tx.ulCurrentSequenceNumber;
  2524. if( ( pxSocket->u.xTCP.bits.bFinAccepted != pdFALSE_UNSIGNED ) || ( ( ucTCPFlags & ( uint8_t ) tcpTCP_FLAG_FIN ) != 0U ) )
  2525. {
  2526. /* Peer is requesting to stop, see if we're really finished. */
  2527. xMayClose = pdTRUE;
  2528. /* Checks are only necessary if we haven't sent a FIN yet. */
  2529. if( pxSocket->u.xTCP.bits.bFinSent == pdFALSE_UNSIGNED )
  2530. {
  2531. /* xTCPWindowTxDone returns true when all Tx queues are empty. */
  2532. bRxComplete = xTCPWindowRxEmpty( pxTCPWindow );
  2533. bTxDone = xTCPWindowTxDone( pxTCPWindow );
  2534. if( ( bRxComplete == 0 ) || ( bTxDone == 0 ) )
  2535. {
  2536. /* Refusing FIN: Rx incomplete 1 optlen 4 tx done 1. */
  2537. FreeRTOS_debug_printf( ( "Refusing FIN[%u,%u]: RxCompl %lu tx done %ld\n",
  2538. pxSocket->usLocalPort,
  2539. pxSocket->u.xTCP.usRemotePort,
  2540. bRxComplete, bTxDone ) );
  2541. xMayClose = pdFALSE;
  2542. }
  2543. else
  2544. {
  2545. ulIntermediateResult = ulSequenceNumber + ulReceiveLength - pxTCPWindow->rx.ulCurrentSequenceNumber;
  2546. lDistance = ( int32_t ) ulIntermediateResult;
  2547. if( lDistance > 1 )
  2548. {
  2549. FreeRTOS_debug_printf( ( "Refusing FIN: Rx not complete %ld (cur %lu high %lu)\n",
  2550. lDistance, pxTCPWindow->rx.ulCurrentSequenceNumber - pxTCPWindow->rx.ulFirstSequenceNumber,
  2551. pxTCPWindow->rx.ulHighestSequenceNumber - pxTCPWindow->rx.ulFirstSequenceNumber ) );
  2552. xMayClose = pdFALSE;
  2553. }
  2554. }
  2555. }
  2556. if( xTCPWindowLoggingLevel > 0 )
  2557. {
  2558. FreeRTOS_debug_printf( ( "TCP: FIN received, mayClose = %ld (Rx %lu Len %ld, Tx %lu)\n",
  2559. xMayClose, ulSequenceNumber - pxSocket->u.xTCP.xTCPWindow.rx.ulFirstSequenceNumber, ulReceiveLength,
  2560. pxTCPWindow->tx.ulCurrentSequenceNumber - pxSocket->u.xTCP.xTCPWindow.tx.ulFirstSequenceNumber ) );
  2561. }
  2562. if( xMayClose != pdFALSE )
  2563. {
  2564. pxSocket->u.xTCP.bits.bFinAccepted = pdTRUE_UNSIGNED;
  2565. xSendLength = prvTCPHandleFin( pxSocket, *ppxNetworkBuffer );
  2566. }
  2567. }
  2568. if( xMayClose == pdFALSE )
  2569. {
  2570. pxTCPHeader->ucTCPFlags = tcpTCP_FLAG_ACK;
  2571. if( ulReceiveLength != 0U )
  2572. {
  2573. uxIntermediateResult = uxIPHeaderSizeSocket( pxSocket ) + ipSIZE_OF_TCP_HEADER + uxOptionsLength;
  2574. xSendLength = ( BaseType_t ) uxIntermediateResult;
  2575. /* TCP-offset equals '( ( length / 4 ) << 4 )', resulting in a shift-left 2 */
  2576. pxTCPHeader->ucTCPOffset = ( uint8_t ) ( ( ipSIZE_OF_TCP_HEADER + uxOptionsLength ) << 2 );
  2577. if( pxSocket->u.xTCP.bits.bFinSent != pdFALSE_UNSIGNED )
  2578. {
  2579. pxTCPWindow->tx.ulCurrentSequenceNumber = pxTCPWindow->tx.ulFINSequenceNumber;
  2580. }
  2581. }
  2582. /* Now get data to be transmitted. */
  2583. /* _HT_ patch: since the MTU has be fixed at 1500 in stead of 1526, TCP
  2584. * can not send-out both TCP options and also a full packet. Sending
  2585. * options (SACK) is always more urgent than sending data, which can be
  2586. * sent later. */
  2587. if( uxOptionsLength == 0U )
  2588. {
  2589. /* prvTCPPrepareSend might allocate a bigger network buffer, if
  2590. * necessary. */
  2591. lSendResult = prvTCPPrepareSend( pxSocket, ppxNetworkBuffer, uxOptionsLength );
  2592. if( lSendResult > 0 )
  2593. {
  2594. xSendLength = ( BaseType_t ) lSendResult;
  2595. }
  2596. }
  2597. }
  2598. return xSendLength;
  2599. }
  2600. /*-----------------------------------------------------------*/
  2601. /**
  2602. * @brief Called from prvTCPHandleState(). There is data to be sent. If
  2603. * ipconfigUSE_TCP_WIN is defined, and if only an ACK must be sent, it will be
  2604. * checked if it would better be postponed for efficiency.
  2605. *
  2606. * @param[in] pxSocket: The socket owning the TCP connection.
  2607. * @param[in] ppxNetworkBuffer: Pointer to pointer to the network buffer.
  2608. * @param[in] ulReceiveLength: The length of the received buffer.
  2609. * @param[in] xByteCount: Length of the data to be sent.
  2610. *
  2611. * @return The number of bytes actually sent.
  2612. */
  2613. static BaseType_t prvSendData( FreeRTOS_Socket_t * pxSocket,
  2614. NetworkBufferDescriptor_t ** ppxNetworkBuffer,
  2615. uint32_t ulReceiveLength,
  2616. BaseType_t xByteCount )
  2617. {
  2618. /* Map the buffer onto the ProtocolHeader_t struct for easy access to the fields. */
  2619. const ProtocolHeaders_t * pxProtocolHeaders = ipCAST_PTR_TO_TYPE_PTR( ProtocolHeaders_t,
  2620. &( ( *ppxNetworkBuffer )->pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER + xIPHeaderSize( *ppxNetworkBuffer ) ] ) );
  2621. const TCPHeader_t * pxTCPHeader = &pxProtocolHeaders->xTCPHeader;
  2622. const TCPWindow_t * pxTCPWindow = &pxSocket->u.xTCP.xTCPWindow;
  2623. /* Find out what window size we may advertised. */
  2624. int32_t lRxSpace;
  2625. BaseType_t xSendLength = xByteCount;
  2626. uint32_t ulRxBufferSpace;
  2627. #if ( ipconfigUSE_TCP_WIN == 1 )
  2628. #if ( ipconfigTCP_ACK_EARLIER_PACKET == 0 )
  2629. const int32_t lMinLength = 0;
  2630. #else
  2631. int32_t lMinLength;
  2632. #endif
  2633. #endif
  2634. /* Set the time-out field, so that we'll be called by the IP-task in case no
  2635. * next message will be received. */
  2636. ulRxBufferSpace = pxSocket->u.xTCP.ulHighestRxAllowed - pxTCPWindow->rx.ulCurrentSequenceNumber;
  2637. lRxSpace = ( int32_t ) ulRxBufferSpace;
  2638. #if ipconfigUSE_TCP_WIN == 1
  2639. {
  2640. #if ( ipconfigTCP_ACK_EARLIER_PACKET != 0 )
  2641. {
  2642. lMinLength = ( ( int32_t ) 2 ) * ( ( int32_t ) pxSocket->u.xTCP.usCurMSS );
  2643. }
  2644. #endif /* ipconfigTCP_ACK_EARLIER_PACKET */
  2645. /* In case we're receiving data continuously, we might postpone sending
  2646. * an ACK to gain performance. */
  2647. /* lint e9007 is OK because 'uxIPHeaderSizeSocket()' has no side-effects. */
  2648. if( ( ulReceiveLength > 0U ) && /* Data was sent to this socket. */
  2649. ( lRxSpace >= lMinLength ) && /* There is Rx space for more data. */
  2650. ( pxSocket->u.xTCP.bits.bFinSent == pdFALSE_UNSIGNED ) && /* Not in a closure phase. */
  2651. ( xSendLength == uxIPHeaderSizeSocket( pxSocket ) + ipSIZE_OF_TCP_HEADER ) && /* No Tx data or options to be sent. */
  2652. ( pxSocket->u.xTCP.ucTCPState == ( uint8_t ) eESTABLISHED ) && /* Connection established. */
  2653. ( pxTCPHeader->ucTCPFlags == tcpTCP_FLAG_ACK ) ) /* There are no other flags than an ACK. */
  2654. {
  2655. if( pxSocket->u.xTCP.pxAckMessage != *ppxNetworkBuffer )
  2656. {
  2657. /* There was still a delayed in queue, delete it. */
  2658. if( pxSocket->u.xTCP.pxAckMessage != NULL )
  2659. {
  2660. vReleaseNetworkBufferAndDescriptor( pxSocket->u.xTCP.pxAckMessage );
  2661. }
  2662. pxSocket->u.xTCP.pxAckMessage = *ppxNetworkBuffer;
  2663. }
  2664. if( ( ulReceiveLength < ( uint32_t ) pxSocket->u.xTCP.usCurMSS ) || /* Received a small message. */
  2665. ( lRxSpace < ipNUMERIC_CAST( int32_t, 2U * pxSocket->u.xTCP.usCurMSS ) ) ) /* There are less than 2 x MSS space in the Rx buffer. */
  2666. {
  2667. pxSocket->u.xTCP.usTimeout = ( uint16_t ) tcpDELAYED_ACK_SHORT_DELAY_MS;
  2668. }
  2669. else
  2670. {
  2671. /* Normally a delayed ACK should wait 200 ms for a next incoming
  2672. * packet. Only wait 20 ms here to gain performance. A slow ACK
  2673. * for full-size message. */
  2674. pxSocket->u.xTCP.usTimeout = ( uint16_t ) ipMS_TO_MIN_TICKS( tcpDELAYED_ACK_LONGER_DELAY_MS );
  2675. }
  2676. if( ( xTCPWindowLoggingLevel > 1 ) && ( ipconfigTCP_MAY_LOG_PORT( pxSocket->usLocalPort ) ) )
  2677. {
  2678. FreeRTOS_debug_printf( ( "Send[%u->%u] del ACK %lu SEQ %lu (len %lu) tmout %u d %lu\n",
  2679. pxSocket->usLocalPort,
  2680. pxSocket->u.xTCP.usRemotePort,
  2681. pxTCPWindow->rx.ulCurrentSequenceNumber - pxTCPWindow->rx.ulFirstSequenceNumber,
  2682. pxSocket->u.xTCP.xTCPWindow.ulOurSequenceNumber - pxTCPWindow->tx.ulFirstSequenceNumber,
  2683. xSendLength,
  2684. pxSocket->u.xTCP.usTimeout, lRxSpace ) );
  2685. }
  2686. *ppxNetworkBuffer = NULL;
  2687. xSendLength = 0;
  2688. }
  2689. else if( pxSocket->u.xTCP.pxAckMessage != NULL )
  2690. {
  2691. /* As an ACK is not being delayed, remove any earlier delayed ACK
  2692. * message. */
  2693. if( pxSocket->u.xTCP.pxAckMessage != *ppxNetworkBuffer )
  2694. {
  2695. vReleaseNetworkBufferAndDescriptor( pxSocket->u.xTCP.pxAckMessage );
  2696. }
  2697. pxSocket->u.xTCP.pxAckMessage = NULL;
  2698. }
  2699. else
  2700. {
  2701. /* The ack will not be postponed, and there was no stored ack ( in 'pxAckMessage' ). */
  2702. }
  2703. }
  2704. #else /* if ipconfigUSE_TCP_WIN == 1 */
  2705. {
  2706. /* Remove compiler warnings. */
  2707. ( void ) ulReceiveLength;
  2708. ( void ) pxTCPHeader;
  2709. ( void ) lRxSpace;
  2710. }
  2711. #endif /* ipconfigUSE_TCP_WIN */
  2712. if( xSendLength != 0 )
  2713. {
  2714. if( ( xTCPWindowLoggingLevel > 1 ) && ( ipconfigTCP_MAY_LOG_PORT( pxSocket->usLocalPort ) ) )
  2715. {
  2716. FreeRTOS_debug_printf( ( "Send[%u->%u] imm ACK %lu SEQ %lu (len %lu)\n",
  2717. pxSocket->usLocalPort,
  2718. pxSocket->u.xTCP.usRemotePort,
  2719. pxTCPWindow->rx.ulCurrentSequenceNumber - pxTCPWindow->rx.ulFirstSequenceNumber,
  2720. pxTCPWindow->ulOurSequenceNumber - pxTCPWindow->tx.ulFirstSequenceNumber,
  2721. xSendLength ) );
  2722. }
  2723. /* Set the parameter 'xReleaseAfterSend' to the value of
  2724. * ipconfigZERO_COPY_TX_DRIVER. */
  2725. prvTCPReturnPacket( pxSocket, *ppxNetworkBuffer, ( uint32_t ) xSendLength, ipconfigZERO_COPY_TX_DRIVER );
  2726. #if ( ipconfigZERO_COPY_TX_DRIVER != 0 )
  2727. {
  2728. /* The driver has taken ownership of the Network Buffer. */
  2729. *ppxNetworkBuffer = NULL;
  2730. }
  2731. #endif
  2732. }
  2733. return xSendLength;
  2734. }
  2735. /*-----------------------------------------------------------*/
  2736. /**
  2737. * @brief Check incoming packets for valid data and handle the state of the
  2738. * TCP connection and respond according to the situation.
  2739. *
  2740. * @param[in] pxSocket: The socket whose connection state is being handled.
  2741. * @param[in] ppxNetworkBuffer: The network buffer descriptor holding the
  2742. * packet received from the peer.
  2743. *
  2744. * @return If the data is correct and some packet was sent to the peer, then
  2745. * the number of bytes sent is returned, or else a negative value is
  2746. * returned indicating an error.
  2747. *
  2748. * @note prvTCPHandleState() is the most important function of this TCP stack
  2749. * We've tried to keep it (relatively short) by putting a lot of code in
  2750. * the static functions above:
  2751. *
  2752. * prvCheckRxData()
  2753. * prvStoreRxData()
  2754. * prvSetOptions()
  2755. * prvHandleSynReceived()
  2756. * prvHandleEstablished()
  2757. * prvSendData()
  2758. *
  2759. * As these functions are declared static, and they're called from one location
  2760. * only, most compilers will inline them, thus avoiding a call and return.
  2761. */
  2762. static BaseType_t prvTCPHandleState( FreeRTOS_Socket_t * pxSocket,
  2763. NetworkBufferDescriptor_t ** ppxNetworkBuffer )
  2764. {
  2765. /* Map the buffer onto the ProtocolHeader_t struct for easy access to the fields. */
  2766. ProtocolHeaders_t * pxProtocolHeaders = ipCAST_PTR_TO_TYPE_PTR( ProtocolHeaders_t,
  2767. &( ( *ppxNetworkBuffer )->pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER + xIPHeaderSize( *ppxNetworkBuffer ) ] ) );
  2768. TCPHeader_t * pxTCPHeader = &( pxProtocolHeaders->xTCPHeader );
  2769. BaseType_t xSendLength = 0;
  2770. uint32_t ulReceiveLength; /* Number of bytes contained in the TCP message. */
  2771. uint8_t * pucRecvData;
  2772. uint32_t ulSequenceNumber = FreeRTOS_ntohl( pxTCPHeader->ulSequenceNumber );
  2773. /* uxOptionsLength: the size of the options to be sent (always a multiple of
  2774. * 4 bytes)
  2775. * 1. in the SYN phase, we shall communicate the MSS
  2776. * 2. in case of a SACK, Selective ACK, ack a segment which comes in
  2777. * out-of-order. */
  2778. UBaseType_t uxOptionsLength = 0U;
  2779. uint8_t ucTCPFlags = pxTCPHeader->ucTCPFlags;
  2780. TCPWindow_t * pxTCPWindow = &( pxSocket->u.xTCP.xTCPWindow );
  2781. UBaseType_t uxIntermediateResult = 0;
  2782. /* First get the length and the position of the received data, if any.
  2783. * pucRecvData will point to the first byte of the TCP payload. */
  2784. ulReceiveLength = ( uint32_t ) prvCheckRxData( *ppxNetworkBuffer, &pucRecvData );
  2785. if( pxSocket->u.xTCP.ucTCPState >= ( uint8_t ) eESTABLISHED )
  2786. {
  2787. if( pxTCPWindow->rx.ulCurrentSequenceNumber == ( ulSequenceNumber + 1UL ) )
  2788. {
  2789. /* This is most probably a keep-alive message from peer. Setting
  2790. * 'bWinChange' doesn't cause a window-size-change, the flag is used
  2791. * here to force sending an immediate ACK. */
  2792. pxSocket->u.xTCP.bits.bWinChange = pdTRUE_UNSIGNED;
  2793. }
  2794. }
  2795. /* Keep track of the highest sequence number that might be expected within
  2796. * this connection. */
  2797. if( ( ( int32_t ) ( ulSequenceNumber + ulReceiveLength - pxTCPWindow->rx.ulHighestSequenceNumber ) ) > 0L )
  2798. {
  2799. pxTCPWindow->rx.ulHighestSequenceNumber = ulSequenceNumber + ulReceiveLength;
  2800. }
  2801. /* Storing data may result in a fatal error if malloc() fails. */
  2802. if( prvStoreRxData( pxSocket, pucRecvData, *ppxNetworkBuffer, ulReceiveLength ) < 0 )
  2803. {
  2804. xSendLength = -1;
  2805. }
  2806. else
  2807. {
  2808. uxOptionsLength = prvSetOptions( pxSocket, *ppxNetworkBuffer );
  2809. if( ( pxSocket->u.xTCP.ucTCPState == ( uint8_t ) eSYN_RECEIVED ) && ( ( ucTCPFlags & ( uint8_t ) tcpTCP_FLAG_CTRL ) == ( uint8_t ) tcpTCP_FLAG_SYN ) )
  2810. {
  2811. FreeRTOS_debug_printf( ( "eSYN_RECEIVED: ACK expected, not SYN: peer missed our SYN+ACK\n" ) );
  2812. /* In eSYN_RECEIVED a simple ACK is expected, but apparently the
  2813. * 'SYN+ACK' didn't arrive. Step back to the previous state in which
  2814. * a first incoming SYN is handled. The SYN was counted already so
  2815. * decrease it first. */
  2816. vTCPStateChange( pxSocket, eSYN_FIRST );
  2817. }
  2818. if( ( ( ucTCPFlags & tcpTCP_FLAG_FIN ) != 0U ) && ( pxSocket->u.xTCP.bits.bFinRecv == pdFALSE_UNSIGNED ) )
  2819. {
  2820. /* It's the first time a FIN has been received, remember its
  2821. * sequence number. */
  2822. pxTCPWindow->rx.ulFINSequenceNumber = ulSequenceNumber + ulReceiveLength;
  2823. pxSocket->u.xTCP.bits.bFinRecv = pdTRUE_UNSIGNED;
  2824. /* Was peer the first one to send a FIN? */
  2825. if( pxSocket->u.xTCP.bits.bFinSent == pdFALSE_UNSIGNED )
  2826. {
  2827. /* If so, don't send the-last-ACK. */
  2828. pxSocket->u.xTCP.bits.bFinLast = pdTRUE_UNSIGNED;
  2829. }
  2830. }
  2831. switch( ipNUMERIC_CAST( eIPTCPState_t, pxSocket->u.xTCP.ucTCPState ) )
  2832. {
  2833. case eCLOSED: /* (server + client) no connection state at all. */
  2834. /* Nothing to do for a closed socket, except waiting for the
  2835. * owner. */
  2836. break;
  2837. case eTCP_LISTEN: /* (server) waiting for a connection request from
  2838. * any remote TCP and port. */
  2839. /* The listen state was handled in xProcessReceivedTCPPacket().
  2840. * Should not come here. */
  2841. break;
  2842. case eSYN_FIRST: /* (server) Just received a SYN request for a server
  2843. * socket. */
  2844. /* A new socket has been created, reply with a SYN+ACK.
  2845. * Acknowledge with seq+1 because the SYN is seen as pseudo data
  2846. * with len = 1. */
  2847. uxOptionsLength = prvSetSynAckOptions( pxSocket, pxTCPHeader );
  2848. pxTCPHeader->ucTCPFlags = ( uint8_t ) tcpTCP_FLAG_SYN | ( uint8_t ) tcpTCP_FLAG_ACK;
  2849. uxIntermediateResult = uxIPHeaderSizeSocket( pxSocket ) + ipSIZE_OF_TCP_HEADER + uxOptionsLength;
  2850. xSendLength = ( BaseType_t ) uxIntermediateResult;
  2851. /* Set the TCP offset field: ipSIZE_OF_TCP_HEADER equals 20 and
  2852. * uxOptionsLength is a multiple of 4. The complete expression is:
  2853. * ucTCPOffset = ( ( ipSIZE_OF_TCP_HEADER + uxOptionsLength ) / 4 ) << 4 */
  2854. pxTCPHeader->ucTCPOffset = ( uint8_t ) ( ( ipSIZE_OF_TCP_HEADER + uxOptionsLength ) << 2 );
  2855. vTCPStateChange( pxSocket, eSYN_RECEIVED );
  2856. pxTCPWindow->rx.ulHighestSequenceNumber = ulSequenceNumber + 1UL;
  2857. pxTCPWindow->rx.ulCurrentSequenceNumber = ulSequenceNumber + 1UL;
  2858. pxTCPWindow->ulNextTxSequenceNumber = pxTCPWindow->tx.ulFirstSequenceNumber + 1UL;
  2859. pxTCPWindow->tx.ulCurrentSequenceNumber = pxTCPWindow->tx.ulFirstSequenceNumber + 1UL; /* because we send a TCP_SYN. */
  2860. break;
  2861. case eCONNECT_SYN: /* (client) also called SYN_SENT: we've just send a
  2862. * SYN, expect a SYN+ACK and send a ACK now. */
  2863. /* Fall through */
  2864. case eSYN_RECEIVED: /* (server) we've had a SYN, replied with SYN+SCK
  2865. * expect a ACK and do nothing. */
  2866. xSendLength = prvHandleSynReceived( pxSocket, *( ppxNetworkBuffer ), ulReceiveLength, uxOptionsLength );
  2867. break;
  2868. case eESTABLISHED: /* (server + client) an open connection, data
  2869. * received can be delivered to the user. The normal
  2870. * state for the data transfer phase of the connection
  2871. * The closing states are also handled here with the
  2872. * use of some flags. */
  2873. xSendLength = prvHandleEstablished( pxSocket, ppxNetworkBuffer, ulReceiveLength, uxOptionsLength );
  2874. break;
  2875. case eLAST_ACK: /* (server + client) waiting for an acknowledgement
  2876. * of the connection termination request previously
  2877. * sent to the remote TCP (which includes an
  2878. * acknowledgement of its connection termination
  2879. * request). */
  2880. /* Fall through */
  2881. case eFIN_WAIT_1: /* (server + client) waiting for a connection termination request from the remote TCP,
  2882. * or an acknowledgement of the connection termination request previously sent. */
  2883. /* Fall through */
  2884. case eFIN_WAIT_2: /* (server + client) waiting for a connection termination request from the remote TCP. */
  2885. xSendLength = prvTCPHandleFin( pxSocket, *ppxNetworkBuffer );
  2886. break;
  2887. case eCLOSE_WAIT: /* (server + client) waiting for a connection
  2888. * termination request from the local user. Nothing to
  2889. * do, connection is closed, wait for owner to close
  2890. * this socket. */
  2891. break;
  2892. case eCLOSING: /* (server + client) waiting for a connection
  2893. * termination request acknowledgement from the remote
  2894. * TCP. */
  2895. break;
  2896. case eTIME_WAIT: /* (either server or client) waiting for enough time
  2897. * to pass to be sure the remote TCP received the
  2898. * acknowledgement of its connection termination
  2899. * request. [According to RFC 793 a connection can stay
  2900. * in TIME-WAIT for a maximum of four minutes known as
  2901. * a MSL (maximum segment lifetime).] These states are
  2902. * implemented implicitly by settings flags like
  2903. * 'bFinSent', 'bFinRecv', and 'bFinAcked'. */
  2904. break;
  2905. default:
  2906. /* No more known states. */
  2907. break;
  2908. }
  2909. }
  2910. if( xSendLength > 0 )
  2911. {
  2912. xSendLength = prvSendData( pxSocket, ppxNetworkBuffer, ulReceiveLength, xSendLength );
  2913. }
  2914. return xSendLength;
  2915. }
  2916. /*-----------------------------------------------------------*/
  2917. /**
  2918. * @brief Common code for sending a TCP protocol control packet (i.e. no options, no
  2919. * payload, just flags).
  2920. *
  2921. * @param[in] pxNetworkBuffer: The network buffer received from the peer.
  2922. * @param[in] ucTCPFlags: The flags to determine what kind of packet this is.
  2923. *
  2924. * @return pdFAIL always indicating that the packet was not consumed.
  2925. */
  2926. static BaseType_t prvTCPSendSpecialPacketHelper( NetworkBufferDescriptor_t * pxNetworkBuffer,
  2927. uint8_t ucTCPFlags )
  2928. {
  2929. #if ( ipconfigIGNORE_UNKNOWN_PACKETS == 1 )
  2930. /* Configured to ignore unknown packets just suppress a compiler warning. */
  2931. ( void ) pxNetworkBuffer;
  2932. ( void ) ucTCPFlags;
  2933. #else
  2934. {
  2935. /* Map the ethernet buffer onto the TCPPacket_t struct for easy access to the fields. */
  2936. TCPPacket_t * pxTCPPacket = ipCAST_PTR_TO_TYPE_PTR( TCPPacket_t, pxNetworkBuffer->pucEthernetBuffer );
  2937. const uint32_t ulSendLength =
  2938. ( ipSIZE_OF_IPv4_HEADER + ipSIZE_OF_TCP_HEADER ); /* Plus 0 options. */
  2939. pxTCPPacket->xTCPHeader.ucTCPFlags = ucTCPFlags;
  2940. pxTCPPacket->xTCPHeader.ucTCPOffset = ( ipSIZE_OF_TCP_HEADER ) << 2;
  2941. prvTCPReturnPacket( NULL, pxNetworkBuffer, ulSendLength, pdFALSE );
  2942. }
  2943. #endif /* !ipconfigIGNORE_UNKNOWN_PACKETS */
  2944. /* The packet was not consumed. */
  2945. return pdFAIL;
  2946. }
  2947. /*-----------------------------------------------------------*/
  2948. /**
  2949. * @brief A "challenge ACK" is as per https://tools.ietf.org/html/rfc5961#section-3.2,
  2950. * case #3. In summary, an RST was received with a sequence number that is
  2951. * unexpected but still within the window.
  2952. *
  2953. * @param[in] pxNetworkBuffer: The network buffer descriptor with the packet.
  2954. *
  2955. * @return Returns the value back from #prvTCPSendSpecialPacketHelper.
  2956. */
  2957. static BaseType_t prvTCPSendChallengeAck( NetworkBufferDescriptor_t * pxNetworkBuffer )
  2958. {
  2959. return prvTCPSendSpecialPacketHelper( pxNetworkBuffer, tcpTCP_FLAG_ACK );
  2960. }
  2961. /*-----------------------------------------------------------*/
  2962. /**
  2963. * @brief Send a RST (Reset) to peer in case the packet cannot be handled.
  2964. *
  2965. * @param[in] pxNetworkBuffer: The network buffer descriptor with the packet.
  2966. *
  2967. * @return Returns the value back from #prvTCPSendSpecialPacketHelper.
  2968. */
  2969. static BaseType_t prvTCPSendReset( NetworkBufferDescriptor_t * pxNetworkBuffer )
  2970. {
  2971. return prvTCPSendSpecialPacketHelper( pxNetworkBuffer,
  2972. ( uint8_t ) tcpTCP_FLAG_ACK | ( uint8_t ) tcpTCP_FLAG_RST );
  2973. }
  2974. /*-----------------------------------------------------------*/
  2975. /**
  2976. * @brief Set the MSS (Maximum segment size) associated with the given socket.
  2977. *
  2978. * @param[in] pxSocket: The socket whose MSS is to be set.
  2979. */
  2980. static void prvSocketSetMSS( FreeRTOS_Socket_t * pxSocket )
  2981. {
  2982. uint32_t ulMSS = ipconfigTCP_MSS;
  2983. if( ( ( FreeRTOS_ntohl( pxSocket->u.xTCP.ulRemoteIP ) ^ *ipLOCAL_IP_ADDRESS_POINTER ) & xNetworkAddressing.ulNetMask ) != 0UL )
  2984. {
  2985. /* Data for this peer will pass through a router, and maybe through
  2986. * the internet. Limit the MSS to 1400 bytes or less. */
  2987. ulMSS = FreeRTOS_min_uint32( ( uint32_t ) tcpREDUCED_MSS_THROUGH_INTERNET, ulMSS );
  2988. }
  2989. FreeRTOS_debug_printf( ( "prvSocketSetMSS: %lu bytes for %lxip:%u\n", ulMSS, pxSocket->u.xTCP.ulRemoteIP, pxSocket->u.xTCP.usRemotePort ) );
  2990. pxSocket->u.xTCP.usInitMSS = ( uint16_t ) ulMSS;
  2991. pxSocket->u.xTCP.usCurMSS = ( uint16_t ) ulMSS;
  2992. }
  2993. /*-----------------------------------------------------------*/
  2994. /**
  2995. * @brief Process the received TCP packet.
  2996. *
  2997. * @param[in] pxDescriptor: The descriptor in which the TCP packet is held.
  2998. *
  2999. * @return If the processing of the packet was successful, then pdPASS is returned
  3000. * or else pdFAIL.
  3001. *
  3002. * @note FreeRTOS_TCP_IP has only 2 public functions, this is the second one:
  3003. * xProcessReceivedTCPPacket()
  3004. * prvTCPHandleState()
  3005. * prvTCPPrepareSend()
  3006. * prvTCPReturnPacket()
  3007. * xNetworkInterfaceOutput() // Sends data to the NIC
  3008. * prvTCPSendRepeated()
  3009. * prvTCPReturnPacket() // Prepare for returning
  3010. * xNetworkInterfaceOutput() // Sends data to the NIC
  3011. */
  3012. BaseType_t xProcessReceivedTCPPacket( NetworkBufferDescriptor_t * pxDescriptor )
  3013. {
  3014. /* Function might modify the parameter. */
  3015. NetworkBufferDescriptor_t * pxNetworkBuffer = pxDescriptor;
  3016. /* Map the buffer onto a ProtocolHeaders_t struct for easy access to the fields. */
  3017. const ProtocolHeaders_t * pxProtocolHeaders = ipCAST_CONST_PTR_TO_CONST_TYPE_PTR( ProtocolHeaders_t,
  3018. &( pxNetworkBuffer->pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER + xIPHeaderSize( pxNetworkBuffer ) ] ) );
  3019. FreeRTOS_Socket_t * pxSocket;
  3020. uint16_t ucTCPFlags = pxProtocolHeaders->xTCPHeader.ucTCPFlags;
  3021. uint32_t ulLocalIP;
  3022. uint16_t xLocalPort = FreeRTOS_htons( pxProtocolHeaders->xTCPHeader.usDestinationPort );
  3023. uint16_t xRemotePort = FreeRTOS_htons( pxProtocolHeaders->xTCPHeader.usSourcePort );
  3024. uint32_t ulRemoteIP;
  3025. uint32_t ulSequenceNumber = FreeRTOS_ntohl( pxProtocolHeaders->xTCPHeader.ulSequenceNumber );
  3026. uint32_t ulAckNumber = FreeRTOS_ntohl( pxProtocolHeaders->xTCPHeader.ulAckNr );
  3027. BaseType_t xResult = pdPASS;
  3028. configASSERT( pxNetworkBuffer != NULL );
  3029. configASSERT( pxNetworkBuffer->pucEthernetBuffer != NULL );
  3030. const IPHeader_t * pxIPHeader;
  3031. /* Check for a minimum packet size. */
  3032. if( pxNetworkBuffer->xDataLength < ( ipSIZE_OF_ETH_HEADER + xIPHeaderSize( pxNetworkBuffer ) + ipSIZE_OF_TCP_HEADER ) )
  3033. {
  3034. xResult = pdFAIL;
  3035. }
  3036. else
  3037. {
  3038. /* Map the ethernet buffer onto the IPHeader_t struct for easy access to the fields. */
  3039. pxIPHeader = ipCAST_CONST_PTR_TO_CONST_TYPE_PTR( IPHeader_t, &( pxNetworkBuffer->pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER ] ) );
  3040. ulLocalIP = FreeRTOS_htonl( pxIPHeader->ulDestinationIPAddress );
  3041. ulRemoteIP = FreeRTOS_htonl( pxIPHeader->ulSourceIPAddress );
  3042. /* Find the destination socket, and if not found: return a socket listing to
  3043. * the destination PORT. */
  3044. pxSocket = ( FreeRTOS_Socket_t * ) pxTCPSocketLookup( ulLocalIP, xLocalPort, ulRemoteIP, xRemotePort );
  3045. if( ( pxSocket == NULL ) || ( prvTCPSocketIsActive( ipNUMERIC_CAST( eIPTCPState_t, pxSocket->u.xTCP.ucTCPState ) ) == pdFALSE ) )
  3046. {
  3047. /* A TCP messages is received but either there is no socket with the
  3048. * given port number or the there is a socket, but it is in one of these
  3049. * non-active states: eCLOSED, eCLOSE_WAIT, eFIN_WAIT_2, eCLOSING, or
  3050. * eTIME_WAIT. */
  3051. FreeRTOS_debug_printf( ( "TCP: No active socket on port %d (%lxip:%d)\n", xLocalPort, ulRemoteIP, xRemotePort ) );
  3052. /* Send a RST to all packets that can not be handled. As a result
  3053. * the other party will get a ECONN error. There are two exceptions:
  3054. * 1) A packet that already has the RST flag set.
  3055. * 2) A packet that only has the ACK flag set.
  3056. * A packet with only the ACK flag set might be the last ACK in
  3057. * a three-way hand-shake that closes a connection. */
  3058. if( ( ( ucTCPFlags & tcpTCP_FLAG_CTRL ) != tcpTCP_FLAG_ACK ) &&
  3059. ( ( ucTCPFlags & tcpTCP_FLAG_RST ) == 0U ) )
  3060. {
  3061. ( void ) prvTCPSendReset( pxNetworkBuffer );
  3062. }
  3063. /* The packet can't be handled. */
  3064. xResult = pdFAIL;
  3065. }
  3066. else
  3067. {
  3068. pxSocket->u.xTCP.ucRepCount = 0U;
  3069. if( pxSocket->u.xTCP.ucTCPState == ( uint8_t ) eTCP_LISTEN )
  3070. {
  3071. /* The matching socket is in a listening state. Test if the peer
  3072. * has set the SYN flag. */
  3073. if( ( ucTCPFlags & tcpTCP_FLAG_CTRL ) != tcpTCP_FLAG_SYN )
  3074. {
  3075. /* What happens: maybe after a reboot, a client doesn't know the
  3076. * connection had gone. Send a RST in order to get a new connect
  3077. * request. */
  3078. #if ( ipconfigHAS_DEBUG_PRINTF == 1 )
  3079. {
  3080. FreeRTOS_debug_printf( ( "TCP: Server can't handle flags: %s from %lxip:%u to port %u\n",
  3081. prvTCPFlagMeaning( ( UBaseType_t ) ucTCPFlags ), ulRemoteIP, xRemotePort, xLocalPort ) );
  3082. }
  3083. #endif /* ipconfigHAS_DEBUG_PRINTF */
  3084. if( ( ucTCPFlags & tcpTCP_FLAG_RST ) == 0U )
  3085. {
  3086. ( void ) prvTCPSendReset( pxNetworkBuffer );
  3087. }
  3088. xResult = pdFAIL;
  3089. }
  3090. else
  3091. {
  3092. /* prvHandleListen() will either return a newly created socket
  3093. * (if bReuseSocket is false), otherwise it returns the current
  3094. * socket which will later get connected. */
  3095. pxSocket = prvHandleListen( pxSocket, pxNetworkBuffer );
  3096. if( pxSocket == NULL )
  3097. {
  3098. xResult = pdFAIL;
  3099. }
  3100. }
  3101. } /* if( pxSocket->u.xTCP.ucTCPState == eTCP_LISTEN ). */
  3102. else
  3103. {
  3104. /* This is not a socket in listening mode. Check for the RST
  3105. * flag. */
  3106. if( ( ucTCPFlags & tcpTCP_FLAG_RST ) != 0U )
  3107. {
  3108. FreeRTOS_debug_printf( ( "TCP: RST received from %lxip:%u for %u\n", ulRemoteIP, xRemotePort, xLocalPort ) );
  3109. /* Implement https://tools.ietf.org/html/rfc5961#section-3.2. */
  3110. if( pxSocket->u.xTCP.ucTCPState == ( uint8_t ) eCONNECT_SYN )
  3111. {
  3112. /* Per the above RFC, "In the SYN-SENT state ... the RST is
  3113. * acceptable if the ACK field acknowledges the SYN." */
  3114. if( ulAckNumber == ( pxSocket->u.xTCP.xTCPWindow.ulOurSequenceNumber + 1UL ) )
  3115. {
  3116. vTCPStateChange( pxSocket, eCLOSED );
  3117. }
  3118. }
  3119. else
  3120. {
  3121. /* Check whether the packet matches the next expected sequence number. */
  3122. if( ulSequenceNumber == pxSocket->u.xTCP.xTCPWindow.rx.ulCurrentSequenceNumber )
  3123. {
  3124. vTCPStateChange( pxSocket, eCLOSED );
  3125. }
  3126. /* Otherwise, check whether the packet is within the receive window. */
  3127. else if( ( ulSequenceNumber > pxSocket->u.xTCP.xTCPWindow.rx.ulCurrentSequenceNumber ) &&
  3128. ( ulSequenceNumber < ( pxSocket->u.xTCP.xTCPWindow.rx.ulCurrentSequenceNumber +
  3129. pxSocket->u.xTCP.xTCPWindow.xSize.ulRxWindowLength ) ) )
  3130. {
  3131. /* Send a challenge ACK. */
  3132. ( void ) prvTCPSendChallengeAck( pxNetworkBuffer );
  3133. }
  3134. else
  3135. {
  3136. /* Nothing. */
  3137. }
  3138. }
  3139. /* Otherwise, do nothing. In any case, the packet cannot be handled. */
  3140. xResult = pdFAIL;
  3141. }
  3142. else if( ( ( ucTCPFlags & tcpTCP_FLAG_CTRL ) == tcpTCP_FLAG_SYN ) && ( pxSocket->u.xTCP.ucTCPState >= ( uint8_t ) eESTABLISHED ) )
  3143. {
  3144. /* SYN flag while this socket is already connected. */
  3145. FreeRTOS_debug_printf( ( "TCP: SYN unexpected from %lxip:%u\n", ulRemoteIP, xRemotePort ) );
  3146. /* The packet cannot be handled. */
  3147. xResult = pdFAIL;
  3148. }
  3149. else
  3150. {
  3151. /* Update the copy of the TCP header only (skipping eth and IP
  3152. * headers). It might be used later on, whenever data must be sent
  3153. * to the peer. */
  3154. const size_t uxOffset = ipSIZE_OF_ETH_HEADER + uxIPHeaderSizeSocket( pxSocket );
  3155. ( void ) memcpy( ( void * ) ( &( pxSocket->u.xTCP.xPacket.u.ucLastPacket[ uxOffset ] ) ),
  3156. ( const void * ) ( &( pxNetworkBuffer->pucEthernetBuffer[ uxOffset ] ) ),
  3157. ipSIZE_OF_TCP_HEADER );
  3158. }
  3159. }
  3160. }
  3161. if( xResult != pdFAIL )
  3162. {
  3163. uint16_t usWindow;
  3164. /* pxSocket is not NULL when xResult != pdFAIL. */
  3165. configASSERT( pxSocket != NULL );
  3166. /* Touch the alive timers because we received a message for this
  3167. * socket. */
  3168. prvTCPTouchSocket( pxSocket );
  3169. /* Parse the TCP option(s), if present. */
  3170. /* _HT_ : if we're in the SYN phase, and peer does not send a MSS option,
  3171. * then we MUST assume an MSS size of 536 bytes for backward compatibility. */
  3172. /* When there are no TCP options, the TCP offset equals 20 bytes, which is stored as
  3173. * the number 5 (words) in the higher nibble of the TCP-offset byte. */
  3174. if( ( pxProtocolHeaders->xTCPHeader.ucTCPOffset & tcpTCP_OFFSET_LENGTH_BITS ) > tcpTCP_OFFSET_STANDARD_LENGTH )
  3175. {
  3176. prvCheckOptions( pxSocket, pxNetworkBuffer );
  3177. }
  3178. usWindow = FreeRTOS_ntohs( pxProtocolHeaders->xTCPHeader.usWindow );
  3179. pxSocket->u.xTCP.ulWindowSize = ( uint32_t ) usWindow;
  3180. #if ( ipconfigUSE_TCP_WIN == 1 )
  3181. {
  3182. /* rfc1323 : The Window field in a SYN (i.e., a <SYN> or <SYN,ACK>)
  3183. * segment itself is never scaled. */
  3184. if( ( ucTCPFlags & ( uint8_t ) tcpTCP_FLAG_SYN ) == 0U )
  3185. {
  3186. pxSocket->u.xTCP.ulWindowSize =
  3187. ( pxSocket->u.xTCP.ulWindowSize << pxSocket->u.xTCP.ucPeerWinScaleFactor );
  3188. }
  3189. }
  3190. #endif /* ipconfigUSE_TCP_WIN */
  3191. /* In prvTCPHandleState() the incoming messages will be handled
  3192. * depending on the current state of the connection. */
  3193. if( prvTCPHandleState( pxSocket, &pxNetworkBuffer ) > 0 )
  3194. {
  3195. /* prvTCPHandleState() has sent a message, see if there are more to
  3196. * be transmitted. */
  3197. #if ( ipconfigUSE_TCP_WIN == 1 )
  3198. {
  3199. ( void ) prvTCPSendRepeated( pxSocket, &pxNetworkBuffer );
  3200. }
  3201. #endif /* ipconfigUSE_TCP_WIN */
  3202. }
  3203. if( pxNetworkBuffer != NULL )
  3204. {
  3205. /* We must check if the buffer is unequal to NULL, because the
  3206. * socket might keep a reference to it in case a delayed ACK must be
  3207. * sent. */
  3208. vReleaseNetworkBufferAndDescriptor( pxNetworkBuffer );
  3209. #ifndef _lint
  3210. /* Clear pointers that are freed. */
  3211. pxNetworkBuffer = NULL;
  3212. #endif
  3213. }
  3214. /* And finally, calculate when this socket wants to be woken up. */
  3215. ( void ) prvTCPNextTimeout( pxSocket );
  3216. /* Return pdPASS to tell that the network buffer is 'consumed'. */
  3217. xResult = pdPASS;
  3218. }
  3219. }
  3220. /* pdPASS being returned means the buffer has been consumed. */
  3221. return xResult;
  3222. }
  3223. /*-----------------------------------------------------------*/
  3224. /**
  3225. * @brief Handle 'listen' event on the given socket.
  3226. *
  3227. * @param[in] pxSocket: The socket on which the listen occurred.
  3228. * @param[in] pxNetworkBuffer: The network buffer carrying the packet.
  3229. *
  3230. * @return If a new socket/duplicate socket is created, then the pointer to
  3231. * that socket is returned or else, a NULL pointer is returned.
  3232. */
  3233. static FreeRTOS_Socket_t * prvHandleListen( FreeRTOS_Socket_t * pxSocket,
  3234. NetworkBufferDescriptor_t * pxNetworkBuffer )
  3235. {
  3236. /* Map the ethernet buffer onto a TCPPacket_t struct for easy access to the fields. */
  3237. const TCPPacket_t * pxTCPPacket = ipCAST_CONST_PTR_TO_CONST_TYPE_PTR( TCPPacket_t, pxNetworkBuffer->pucEthernetBuffer );
  3238. FreeRTOS_Socket_t * pxReturn = NULL;
  3239. uint32_t ulInitialSequenceNumber;
  3240. /* Assume that a new Initial Sequence Number will be required. Request
  3241. * it now in order to fail out if necessary. */
  3242. ulInitialSequenceNumber = ulApplicationGetNextSequenceNumber( *ipLOCAL_IP_ADDRESS_POINTER,
  3243. pxSocket->usLocalPort,
  3244. pxTCPPacket->xIPHeader.ulSourceIPAddress,
  3245. pxTCPPacket->xTCPHeader.usSourcePort );
  3246. /* A pure SYN (without ACK) has come in, create a new socket to answer
  3247. * it. */
  3248. if( ulInitialSequenceNumber != 0UL )
  3249. {
  3250. if( pxSocket->u.xTCP.bits.bReuseSocket != pdFALSE_UNSIGNED )
  3251. {
  3252. /* The flag bReuseSocket indicates that the same instance of the
  3253. * listening socket should be used for the connection. */
  3254. pxReturn = pxSocket;
  3255. pxSocket->u.xTCP.bits.bPassQueued = pdTRUE_UNSIGNED;
  3256. pxSocket->u.xTCP.pxPeerSocket = pxSocket;
  3257. }
  3258. else
  3259. {
  3260. /* The socket does not have the bReuseSocket flag set meaning create a
  3261. * new socket when a connection comes in. */
  3262. pxReturn = NULL;
  3263. if( pxSocket->u.xTCP.usChildCount >= pxSocket->u.xTCP.usBacklog )
  3264. {
  3265. FreeRTOS_printf( ( "Check: Socket %u already has %u / %u child%s\n",
  3266. pxSocket->usLocalPort,
  3267. pxSocket->u.xTCP.usChildCount,
  3268. pxSocket->u.xTCP.usBacklog,
  3269. ( pxSocket->u.xTCP.usChildCount == 1U ) ? "" : "ren" ) );
  3270. ( void ) prvTCPSendReset( pxNetworkBuffer );
  3271. }
  3272. else
  3273. {
  3274. FreeRTOS_Socket_t * pxNewSocket = ( FreeRTOS_Socket_t * )
  3275. FreeRTOS_socket( FREERTOS_AF_INET, FREERTOS_SOCK_STREAM, FREERTOS_IPPROTO_TCP );
  3276. if( ( pxNewSocket == NULL ) || ( pxNewSocket == FREERTOS_INVALID_SOCKET ) )
  3277. {
  3278. FreeRTOS_debug_printf( ( "TCP: Listen: new socket failed\n" ) );
  3279. ( void ) prvTCPSendReset( pxNetworkBuffer );
  3280. }
  3281. else if( prvTCPSocketCopy( pxNewSocket, pxSocket ) != pdFALSE )
  3282. {
  3283. /* The socket will be connected immediately, no time for the
  3284. * owner to setsockopt's, therefore copy properties of the server
  3285. * socket to the new socket. Only the binding might fail (due to
  3286. * lack of resources). */
  3287. pxReturn = pxNewSocket;
  3288. }
  3289. else
  3290. {
  3291. /* Copying failed somehow. */
  3292. }
  3293. }
  3294. }
  3295. }
  3296. if( ( ulInitialSequenceNumber != 0U ) && ( pxReturn != NULL ) )
  3297. {
  3298. /* Map the byte stream onto the ProtocolHeaders_t for easy access to the fields. */
  3299. const ProtocolHeaders_t * pxProtocolHeaders = ipCAST_CONST_PTR_TO_CONST_TYPE_PTR( ProtocolHeaders_t,
  3300. &( pxNetworkBuffer->pucEthernetBuffer[ ipSIZE_OF_ETH_HEADER + xIPHeaderSize( pxNetworkBuffer ) ] ) );
  3301. pxReturn->u.xTCP.usRemotePort = FreeRTOS_htons( pxTCPPacket->xTCPHeader.usSourcePort );
  3302. pxReturn->u.xTCP.ulRemoteIP = FreeRTOS_htonl( pxTCPPacket->xIPHeader.ulSourceIPAddress );
  3303. pxReturn->u.xTCP.xTCPWindow.ulOurSequenceNumber = ulInitialSequenceNumber;
  3304. /* Here is the SYN action. */
  3305. pxReturn->u.xTCP.xTCPWindow.rx.ulCurrentSequenceNumber = FreeRTOS_ntohl( pxProtocolHeaders->xTCPHeader.ulSequenceNumber );
  3306. prvSocketSetMSS( pxReturn );
  3307. prvTCPCreateWindow( pxReturn );
  3308. vTCPStateChange( pxReturn, eSYN_FIRST );
  3309. /* Make a copy of the header up to the TCP header. It is needed later
  3310. * on, whenever data must be sent to the peer. */
  3311. ( void ) memcpy( ( void * ) pxReturn->u.xTCP.xPacket.u.ucLastPacket,
  3312. ( const void * ) pxNetworkBuffer->pucEthernetBuffer,
  3313. sizeof( pxReturn->u.xTCP.xPacket.u.ucLastPacket ) );
  3314. }
  3315. return pxReturn;
  3316. }
  3317. /*-----------------------------------------------------------*/
  3318. /**
  3319. * @brief Duplicates a socket after a listening socket receives a connection and bind
  3320. * the new socket to the same port as the listening socket.
  3321. * Also, let the new socket inherit all properties from the listening socket.
  3322. *
  3323. * @param[in] pxNewSocket: Pointer to the new socket.
  3324. * @param[in] pxSocket: Pointer to the socket being duplicated.
  3325. *
  3326. * @return If all steps all successful, then pdTRUE is returned. Else, pdFALSE.
  3327. */
  3328. static BaseType_t prvTCPSocketCopy( FreeRTOS_Socket_t * pxNewSocket,
  3329. FreeRTOS_Socket_t * pxSocket )
  3330. {
  3331. struct freertos_sockaddr xAddress;
  3332. BaseType_t xResult;
  3333. pxNewSocket->xReceiveBlockTime = pxSocket->xReceiveBlockTime;
  3334. pxNewSocket->xSendBlockTime = pxSocket->xSendBlockTime;
  3335. pxNewSocket->ucSocketOptions = pxSocket->ucSocketOptions;
  3336. pxNewSocket->u.xTCP.uxRxStreamSize = pxSocket->u.xTCP.uxRxStreamSize;
  3337. pxNewSocket->u.xTCP.uxTxStreamSize = pxSocket->u.xTCP.uxTxStreamSize;
  3338. pxNewSocket->u.xTCP.uxLittleSpace = pxSocket->u.xTCP.uxLittleSpace;
  3339. pxNewSocket->u.xTCP.uxEnoughSpace = pxSocket->u.xTCP.uxEnoughSpace;
  3340. pxNewSocket->u.xTCP.uxRxWinSize = pxSocket->u.xTCP.uxRxWinSize;
  3341. pxNewSocket->u.xTCP.uxTxWinSize = pxSocket->u.xTCP.uxTxWinSize;
  3342. #if ( ipconfigSOCKET_HAS_USER_SEMAPHORE == 1 )
  3343. {
  3344. pxNewSocket->pxUserSemaphore = pxSocket->pxUserSemaphore;
  3345. }
  3346. #endif /* ipconfigSOCKET_HAS_USER_SEMAPHORE */
  3347. #if ( ipconfigUSE_CALLBACKS == 1 )
  3348. {
  3349. /* In case call-backs are used, copy them from parent to child. */
  3350. pxNewSocket->u.xTCP.pxHandleConnected = pxSocket->u.xTCP.pxHandleConnected;
  3351. pxNewSocket->u.xTCP.pxHandleReceive = pxSocket->u.xTCP.pxHandleReceive;
  3352. pxNewSocket->u.xTCP.pxHandleSent = pxSocket->u.xTCP.pxHandleSent;
  3353. }
  3354. #endif /* ipconfigUSE_CALLBACKS */
  3355. #if ( ipconfigSUPPORT_SELECT_FUNCTION == 1 )
  3356. {
  3357. /* Child socket of listening sockets will inherit the Socket Set
  3358. * Otherwise the owner has no chance of including it into the set. */
  3359. if( pxSocket->pxSocketSet != NULL )
  3360. {
  3361. pxNewSocket->pxSocketSet = pxSocket->pxSocketSet;
  3362. pxNewSocket->xSelectBits = pxSocket->xSelectBits | ( ( EventBits_t ) eSELECT_READ ) | ( ( EventBits_t ) eSELECT_EXCEPT );
  3363. }
  3364. }
  3365. #endif /* ipconfigSUPPORT_SELECT_FUNCTION */
  3366. /* And bind it to the same local port as its parent. */
  3367. xAddress.sin_addr = *ipLOCAL_IP_ADDRESS_POINTER;
  3368. xAddress.sin_port = FreeRTOS_htons( pxSocket->usLocalPort );
  3369. #if ( ipconfigTCP_HANG_PROTECTION == 1 )
  3370. {
  3371. /* Only when there is anti-hanging protection, a socket may become an
  3372. * orphan temporarily. Once this socket is really connected, the owner of
  3373. * the server socket will be notified. */
  3374. /* When bPassQueued is true, the socket is an orphan until it gets
  3375. * connected. */
  3376. pxNewSocket->u.xTCP.bits.bPassQueued = pdTRUE_UNSIGNED;
  3377. pxNewSocket->u.xTCP.pxPeerSocket = pxSocket;
  3378. }
  3379. #else
  3380. {
  3381. /* A reference to the new socket may be stored and the socket is marked
  3382. * as 'passable'. */
  3383. /* When bPassAccept is true, this socket may be returned in a call to
  3384. * accept(). */
  3385. pxNewSocket->u.xTCP.bits.bPassAccept = pdTRUE_UNSIGNED;
  3386. if( pxSocket->u.xTCP.pxPeerSocket == NULL )
  3387. {
  3388. pxSocket->u.xTCP.pxPeerSocket = pxNewSocket;
  3389. }
  3390. }
  3391. #endif /* if ( ipconfigTCP_HANG_PROTECTION == 1 ) */
  3392. pxSocket->u.xTCP.usChildCount++;
  3393. FreeRTOS_debug_printf( ( "Gain: Socket %u now has %u / %u child%s\n",
  3394. pxSocket->usLocalPort,
  3395. pxSocket->u.xTCP.usChildCount,
  3396. pxSocket->u.xTCP.usBacklog,
  3397. ( pxSocket->u.xTCP.usChildCount == 1U ) ? "" : "ren" ) );
  3398. /* Now bind the child socket to the same port as the listening socket. */
  3399. if( vSocketBind( pxNewSocket, &xAddress, sizeof( xAddress ), pdTRUE ) != 0 )
  3400. {
  3401. FreeRTOS_debug_printf( ( "TCP: Listen: new socket bind error\n" ) );
  3402. ( void ) FreeRTOS_closesocket( pxNewSocket );
  3403. xResult = pdFALSE;
  3404. }
  3405. else
  3406. {
  3407. xResult = pdTRUE;
  3408. }
  3409. return xResult;
  3410. }
  3411. /*-----------------------------------------------------------*/
  3412. #if ( ( ipconfigHAS_DEBUG_PRINTF != 0 ) || ( ipconfigHAS_PRINTF != 0 ) )
  3413. const char * FreeRTOS_GetTCPStateName( UBaseType_t ulState )
  3414. {
  3415. static const char * const pcStateNames[] =
  3416. {
  3417. "eCLOSED",
  3418. "eTCP_LISTEN",
  3419. "eCONNECT_SYN",
  3420. "eSYN_FIRST",
  3421. "eSYN_RECEIVED",
  3422. "eESTABLISHED",
  3423. "eFIN_WAIT_1",
  3424. "eFIN_WAIT_2",
  3425. "eCLOSE_WAIT",
  3426. "eCLOSING",
  3427. "eLAST_ACK",
  3428. "eTIME_WAIT",
  3429. "eUNKNOWN",
  3430. };
  3431. BaseType_t xIndex = ( BaseType_t ) ulState;
  3432. if( ( xIndex < 0 ) || ( xIndex >= ARRAY_SIZE( pcStateNames ) ) )
  3433. {
  3434. /* The last item is called 'eUNKNOWN' */
  3435. xIndex = ARRAY_SIZE( pcStateNames );
  3436. xIndex--;
  3437. }
  3438. return pcStateNames[ xIndex ];
  3439. }
  3440. #endif /* ( ( ipconfigHAS_DEBUG_PRINTF != 0 ) || ( ipconfigHAS_PRINTF != 0 ) ) */
  3441. /*-----------------------------------------------------------*/
  3442. /**
  3443. * @brief In the API accept(), the user asks is there is a new client? As API's can
  3444. * not walk through the xBoundTCPSocketsList the IP-task will do this.
  3445. *
  3446. * @param[in] pxSocket: The socket for which the bound socket list will be iterated.
  3447. *
  3448. * @return if there is a new client, then pdTRUE is returned or else, pdFALSE.
  3449. */
  3450. BaseType_t xTCPCheckNewClient( FreeRTOS_Socket_t * pxSocket )
  3451. {
  3452. TickType_t uxLocalPort = ( TickType_t ) FreeRTOS_htons( pxSocket->usLocalPort );
  3453. const ListItem_t * pxIterator;
  3454. FreeRTOS_Socket_t * pxFound;
  3455. BaseType_t xResult = pdFALSE;
  3456. const ListItem_t * pxEndTCP = listGET_END_MARKER( &xBoundTCPSocketsList );
  3457. /* Here xBoundTCPSocketsList can be accessed safely IP-task is the only one
  3458. * who has access. */
  3459. for( pxIterator = ( const ListItem_t * ) listGET_HEAD_ENTRY( &xBoundTCPSocketsList );
  3460. pxIterator != pxEndTCP;
  3461. pxIterator = ( const ListItem_t * ) listGET_NEXT( pxIterator ) )
  3462. {
  3463. if( listGET_LIST_ITEM_VALUE( pxIterator ) == ( configLIST_VOLATILE TickType_t ) uxLocalPort )
  3464. {
  3465. pxFound = ipCAST_PTR_TO_TYPE_PTR( FreeRTOS_Socket_t, listGET_LIST_ITEM_OWNER( pxIterator ) );
  3466. if( ( pxFound->ucProtocol == ( uint8_t ) FREERTOS_IPPROTO_TCP ) && ( pxFound->u.xTCP.bits.bPassAccept != pdFALSE_UNSIGNED ) )
  3467. {
  3468. pxSocket->u.xTCP.pxPeerSocket = pxFound;
  3469. FreeRTOS_debug_printf( ( "xTCPCheckNewClient[0]: client on port %u\n", pxSocket->usLocalPort ) );
  3470. xResult = pdTRUE;
  3471. break;
  3472. }
  3473. }
  3474. }
  3475. return xResult;
  3476. }
  3477. /*-----------------------------------------------------------*/
  3478. #endif /* ipconfigUSE_TCP == 1 */
  3479. /* Provide access to private members for testing. */
  3480. #ifdef FREERTOS_ENABLE_UNIT_TESTS
  3481. #include "freertos_tcp_test_access_tcp_define.h"
  3482. #endif
  3483. /* Provide access to private members for verification. */
  3484. #ifdef FREERTOS_TCP_ENABLE_VERIFICATION
  3485. #include "aws_freertos_tcp_verification_access_tcp_define.h"
  3486. #endif