Text   |  XML   |  ReML   |   Visible Warnings:

Null Test After Dereference  at packet-tcp.c:1838

No properties have been set. | edit properties
Jump to warning location ↓ warning details...
Show Events | Options

desegment_tcp

(/home/sate/Testcases/c/cve/wireshark-1.2.0/epan/dissectors/packet-tcp.c)expand/collapse
Show more  
 1534  desegment_tcp(tvbuff_t *tvb, packet_info *pinfo, int offset,
 1535                  guint32 seq, guint32 nxtseq,
 1536                  guint32 sport, guint32 dport,
 1537                  proto_tree *tree, proto_tree *tcp_tree,
 1538                  struct tcp_analysis *tcpd)
 1539  {
 1540          struct tcpinfo *tcpinfo = pinfo->private_data;
 1541          fragment_data *ipfd_head;
 1542          int last_fragment_len;
 1543          gboolean must_desegment;
 1544          gboolean called_dissector;
 1545          int another_pdu_follows;
 1546          int deseg_offset;
 1547          guint32 deseg_seq;
 1548          gint nbytes;
 1549          proto_item *item;
 1550          struct tcp_multisegment_pdu *msp;
 1551   
 1552  again:
 1553          ipfd_head=NULL;
 1554          last_fragment_len=0;
 1555          must_desegment = FALSE;
 1556          called_dissector = FALSE;
 1557          another_pdu_follows = 0;
 1558          msp=NULL;
 1559   
 1560          /*
 1561           * Initialize these to assume no desegmentation.
 1562           * If that's not the case, these will be set appropriately 
 1563           * by the subdissector.
 1564           */
 1565          pinfo->desegment_offset = 0;
 1566          pinfo->desegment_len = 0;
 1567   
 1568          /*
 1569           * Initialize this to assume that this segment will just be
 1570           * added to the middle of a desegmented chunk of data, so 
 1571           * that we should show it all as data.
 1572           * If that's not the case, it will be set appropriately.
 1573           */
 1574          deseg_offset = offset;
 1575   
 1576          /* find the most previous PDU starting before this sequence number */
 1577          if (tcpd) {
 1578                  msp = se_tree_lookup32_le(tcpd->fwd->multisegment_pdus, seq-1);
 1579          }
 1580          if(msp && msp->seq<=seq && msp->nxtpdu>seq){
 1581                  int len;
 1582   
 1583                  if(!pinfo->fd->flags.visited){
 1584                          msp->last_frame=pinfo->fd->num;
 1585                          msp->last_frame_time=pinfo->fd->abs_ts;
 1586                  }
 1587   
 1588                  /* OK, this PDU was found, which means the segment continues 
 1589                     a higher-level PDU and that we must desegment it.
 1590                  */
 1591                  if(msp->flags&MSP_FLAGS_REASSEMBLE_ENTIRE_SEGMENT){
 1592                          /* The dissector asked for the entire segment */
 1593                          len=tvb_length_remaining(tvb, offset);
 1594                  } else {
 1595                          len=MIN(nxtseq, msp->nxtpdu) - seq;
 1596                  }
 1597                  last_fragment_len = len;
 1598   
 1599                  ipfd_head = fragment_add(tvb, offset, pinfo, msp->first_frame,
 1600                          tcp_fragment_table,
 1601                          seq - msp->seq,
 1602                          len,
 1603                          (LT_SEQ (nxtseq,msp->nxtpdu)) );
 1604   
 1605                  if(msp->flags&MSP_FLAGS_REASSEMBLE_ENTIRE_SEGMENT){
 1606                          msp->flags&=(~MSP_FLAGS_REASSEMBLE_ENTIRE_SEGMENT);
 1607   
 1608                          /* If we consumed the entire segment there is no 
 1609                           * other pdu starting anywhere inside this segment.
 1610                           * So update nxtpdu to point at least to the start
 1611                           * of the next segment.
 1612                           * (If the subdissector asks for even more data we
 1613                           * will advance nxtpdu even furhter later down in
 1614                           * the code.)
 1615                           */
 1616                          msp->nxtpdu=nxtseq;
 1617                  }
 1618   
 1619                  if( (msp->nxtpdu<nxtseq)
 1620                  &&  (msp->nxtpdu>=seq)
 1621                  &&  (len>0) ){
 1622                          another_pdu_follows=msp->nxtpdu-seq;
 1623                  }
 1624          } else {
 1625                  /* This segment was not found in our table, so it doesn't
 1626                     contain a continuation of a higher-level PDU.
 1627                     Call the normal subdissector.
 1628                  */
 1629                  process_tcp_payload(tvb, offset, pinfo, tree, tcp_tree,
 1630                                  sport, dport, 0, 0, FALSE, tcpd);
 1631                  called_dissector = TRUE;
 1632   
 1633                  /* Did the subdissector ask us to desegment some more data
 1634                     before it could handle the packet?
 1635                     If so we have to create some structures in our table but 
 1636                     this is something we only do the first time we see this 
 1637                     packet.
 1638                  */
 1639                  if(pinfo->desegment_len) {
 1640                          if (!pinfo->fd->flags.visited)
 1641                                  must_desegment = TRUE;
 1642   
 1643                          /*
 1644                           * Set "deseg_offset" to the offset in "tvb"
 1645                           * of the first byte of data that the
 1646                           * subdissector didn't process.
 1647                           */
 1648                          deseg_offset = offset + pinfo->desegment_offset;
 1649                  }
 1650   
 1651                  /* Either no desegmentation is necessary, or this is 
 1652                     segment contains the beginning but not the end of
 1653                     a higher-level PDU and thus isn't completely 
 1654                     desegmented.
 1655                  */
 1656                  ipfd_head = NULL;
 1657          }
 1658   
 1659   
 1660          /* is it completely desegmented? */
 1661          if(ipfd_head){
 1662                  /*
 1663                   * Yes, we think it is.
 1664                   * We only call subdissector for the last segment.
 1665                   * Note that the last segment may include more than what
 1666                   * we needed.
 1667                   */
 1668                  if(ipfd_head->reassembled_in==pinfo->fd->num){
 1669                          /*
 1670                           * OK, this is the last segment.
 1671                           * Let's call the subdissector with the desegmented
 1672                           * data.
 1673                           */
 1674                          tvbuff_t *next_tvb;
 1675                          int old_len;
 1676   
 1677                          /* create a new TVB structure for desegmented data */
 1678                          next_tvb = tvb_new_child_real_data(tvb, ipfd_head->data,
 1679                                          ipfd_head->datalen, ipfd_head->datalen);
 1680   
 1681   
 1682                          /* add desegmented data to the data source list */
 1683                          add_new_data_source(pinfo, next_tvb, "Reassembled TCP");
 1684   
 1685                          /*
 1686                           * Supply the sequence number of the first of the 
 1687                           * reassembled bytes.
 1688                           */
 1689                          tcpinfo->seq = msp->seq;
 1690   
 1691                          /* indicate that this is reassembled data */
 1692                          tcpinfo->is_reassembled = TRUE;
 1693   
 1694                          /* call subdissector */
 1695                          process_tcp_payload(next_tvb, 0, pinfo, tree,
 1696                              tcp_tree, sport, dport, 0, 0, FALSE, tcpd);
 1697                          called_dissector = TRUE;
 1698   
 1699                          /*
 1700                           * OK, did the subdissector think it was completely 
 1701                           * desegmented, or does it think we need even more
 1702                           * data?
 1703                           */
 1704                          old_len=(int)(tvb_reported_length(next_tvb)-last_fragment_len);
 1705                          if(pinfo->desegment_len &&
 1706                              pinfo->desegment_offset<=old_len){
 1707                                  /*
 1708                                   * "desegment_len" isn't 0, so it needs more
 1709                                   * data for something - and "desegment_offset"
 1710                                   * is before "old_len", so it needs more data 
 1711                                   * to dissect the stuff we thought was 
 1712                                   * completely desegmented (as opposed to the 
 1713                                   * stuff at the beginning being completely
 1714                                   * desegmented, but the stuff at the end
 1715                                   * being a new higher-level PDU that also 
 1716                                   * needs desegmentation).
 1717                                   */
 1718                                  fragment_set_partial_reassembly(pinfo,msp->first_frame,tcp_fragment_table);
 1719                                  /* Update msp->nxtpdu to point to the new next
 1720                                   * pdu boundary.
 1721                                   */
 1722                                  if(pinfo->desegment_len==DESEGMENT_ONE_MORE_SEGMENT){
 1723                                          /* We want reassembly of at least one 
 1724                                           * more segment so set the nxtpdu
 1725                                           * boundary to one byte into the next 
 1726                                           * segment.
 1727                                           * This means that the next segment
 1728                                           * will complete reassembly even if it
 1729                                           * is only one single byte in length.
 1730                                           */
 1731                                          msp->nxtpdu=seq+tvb_reported_length_remaining(tvb, offset) + 1;
 1732                                          msp->flags|=MSP_FLAGS_REASSEMBLE_ENTIRE_SEGMENT;
 1733                                  } else {
 1734                                          msp->nxtpdu=seq + last_fragment_len + pinfo->desegment_len;
 1735                                  }
 1736                                  /* Since we need at least some more data
 1737                                   * there can be no pdu following in the
 1738                                   * tail of this segment.
 1739                                   */
 1740                                  another_pdu_follows=0;
 1741                                  offset += last_fragment_len;
 1742                                  seq += last_fragment_len;
 1743                                  if (tvb_length_remaining(tvb, offset) > 0)
 1744                                          goto again;
 1745                          } else {
 1746                                  /*
 1747                                   * Show the stuff in this TCP segment as
 1748                                   * just raw TCP segment data.
 1749                                   */
 1750                                  nbytes = another_pdu_follows > 0 
 1751                                          ? another_pdu_follows 
 1752                                          : tvb_reported_length_remaining(tvb, offset);
 1753                                  proto_tree_add_text(tcp_tree, tvb, offset, nbytes,
 1754                                      "TCP segment data (%u byte%s)", nbytes,
 1755                                      plurality(nbytes, "", "s"));
 1756   
 1757                                  print_tcp_fragment_tree(ipfd_head, tree, tcp_tree, pinfo, next_tvb);
 1758   
 1759                                  /* Did the subdissector ask us to desegment 
 1760                                     some more data?  This means that the data
 1761                                     at the beginning of this segment completed
 1762                                     a higher-level PDU, but the data at the 
 1763                                     end of this segment started a higher-level
 1764                                     PDU but didn't complete it.
 1765   
 1766                                     If so, we have to create some structures
 1767                                     in our table, but this is something we 
 1768                                     only do the first time we see this packet.
 1769                                  */
 1770                                  if(pinfo->desegment_len) {
 1771                                          if (!pinfo->fd->flags.visited)
 1772                                                  must_desegment = TRUE;
 1773   
 1774                                          /* The stuff we couldn't dissect 
 1775                                             must have come from this segment,
 1776                                             so it's all in "tvb".
 1777   
 1778                                             "pinfo->desegment_offset" is 
 1779                                             relative to the beginning of
 1780                                             "next_tvb"; we want an offset
 1781                                             relative to the beginning of "tvb".
 1782   
 1783                                             First, compute the offset relative
 1784                                             to the *end* of "next_tvb" - i.e.,
 1785                                             the number of bytes before the end
 1786                                             of "next_tvb" at which the 
 1787                                             subdissector stopped.  That's the 
 1788                                             length of "next_tvb" minus the
 1789                                             offset, relative to the beginning
 1790                                             of "next_tvb, at which the 
 1791                                             subdissector stopped.
 1792                                          */
 1793                                          deseg_offset =
 1794                                              ipfd_head->datalen - pinfo->desegment_offset;
 1795   
 1796                                          /* "tvb" and "next_tvb" end at the 
 1797                                             same byte of data, so the offset 
 1798                                             relative to the end of "next_tvb"
 1799                                             of the byte at which we stopped
 1800                                             is also the offset relative to 
 1801                                             the end of "tvb" of the byte at
 1802                                             which we stopped.
 1803   
 1804                                             Convert that back into an offset 
 1805                                             relative to the beginninng of
 1806                                             "tvb", by taking the length of 
 1807                                             "tvb" and subtracting the offset
 1808                                             relative to the end.
 1809                                          */
 1810                                          deseg_offset=tvb_reported_length(tvb) - deseg_offset;
 1811                                  }
 1812                          }
 1813                  }
 1814          }
 1815   
 1816          if (must_desegment) {
 1817              /* If the dissector requested "reassemble until FIN"
 1818               * just set this flag for the flow and let reassembly
 1819               * proceed at normal.  We will check/pick up these
 1820               * reassembled PDUs later down in dissect_tcp() when checking
 1821               * for the FIN flag.
 1822               */
 1823              if(tcpd && pinfo->desegment_len==DESEGMENT_UNTIL_FIN) {
 1824                  tcpd->fwd->flags|=TCP_FLOW_REASSEMBLE_UNTIL_FIN;
 1825              }
 1826              /*
 1827               * The sequence number at which the stuff to be desegmented
 1828               * starts is the sequence number of the byte at an offset 
 1829               * of "deseg_offset" into "tvb".
 1830               *
 1831               * The sequence number of the byte at an offset of "offset"
 1832               * is "seq", i.e. the starting sequence number of this
 1833               * segment, so the sequence number of the byte at
 1834               * "deseg_offset" is "seq + (deseg_offset - offset)".
 1835               */
 1836              deseg_seq = seq + (deseg_offset - offset);
 1837   
 1838              if(tcpd && ((nxtseq - deseg_seq) <= 1024*1024)
 1839              &&  (!pinfo->fd->flags.visited) ){
 1840                  if(pinfo->desegment_len==DESEGMENT_ONE_MORE_SEGMENT){
 1841                          /* The subdissector asked to reassemble using the 
 1842                           * entire next segment.
 1843                           * Just ask reassembly for one more byte 
 1844                           * but set this msp flag so we can pick it up 
 1845                           * above.
 1846                           */
 1847                          msp = pdu_store_sequencenumber_of_next_pdu(pinfo,
 1848                                  deseg_seq, nxtseq+1, tcpd->fwd->multisegment_pdus);
 1849                          msp->flags|=MSP_FLAGS_REASSEMBLE_ENTIRE_SEGMENT;
 1850                  } else {
 1851                          msp = pdu_store_sequencenumber_of_next_pdu(pinfo,
 1852                                  deseg_seq, nxtseq+pinfo->desegment_len, tcpd->fwd->multisegment_pdus);
 1853                  }
 1854   
 1855                  /* add this segment as the first one for this new pdu */
 1856                  fragment_add(tvb, deseg_offset, pinfo, msp->first_frame,
 1857                          tcp_fragment_table,
 1858                          0,
 1859                          nxtseq - deseg_seq,
 1860                          LT_SEQ(nxtseq, msp->nxtpdu));
 1861                  }
 1862          }
 1863   
 1864          if (!called_dissector || pinfo->desegment_len != 0) {
 1865                  if (ipfd_head != NULL && ipfd_head->reassembled_in != 0 &&
 1866                      !(ipfd_head->flags & FD_PARTIAL_REASSEMBLY)) {
 1867                          /*
 1868                           * We know what frame this PDU is reassembled in;
 1869                           * let the user know.
 1870                           */
 1871                          item=proto_tree_add_uint(tcp_tree, hf_tcp_reassembled_in,
 1872                              tvb, 0, 0, ipfd_head->reassembled_in);
 1873                          PROTO_ITEM_SET_GENERATED(item);
 1874                  }
 1875   
 1876                  /*
 1877                   * Either we didn't call the subdissector at all (i.e.,
 1878                   * this is a segment that contains the middle of a
 1879                   * higher-level PDU, but contains neither the beginning 
 1880                   * nor the end), or the subdissector couldn't dissect it
 1881                   * all, as some data was missing (i.e., it set
 1882                   * "pinfo->desegment_len" to the amount of additional 
 1883                   * data it needs).
 1884                   */
 1885                  if (pinfo->desegment_offset == 0) {
 1886                          /*
 1887                           * It couldn't, in fact, dissect any of it (the
 1888                           * first byte it couldn't dissect is at an offset 
 1889                           * of "pinfo->desegment_offset" from the beginning 
 1890                           * of the payload, and that's 0).
 1891                           * Just mark this as TCP.
 1892                           */
 1893                          if (check_col(pinfo->cinfo, COL_PROTOCOL)){
 1894                                  col_set_str(pinfo->cinfo, COL_PROTOCOL, "TCP");
 1895                          }
 1896                          if (check_col(pinfo->cinfo, COL_INFO)){
 1897                                  col_set_str(pinfo->cinfo, COL_INFO, "[TCP segment of a reassembled PDU]");
 1898                          }
 1899                  }
 1900   
 1901                  /*
 1902                   * Show what's left in the packet as just raw TCP segment 
 1903                   * data.
 1904                   * XXX - remember what protocol the last subdissector
 1905                   * was, and report it as a continuation of that, instead?
 1906                   */
 1907                  nbytes = tvb_reported_length_remaining(tvb, deseg_offset);
 1908                  proto_tree_add_text(tcp_tree, tvb, deseg_offset, -1,
 1909                      "TCP segment data (%u byte%s)", nbytes,
 1910                      plurality(nbytes, "", "s"));
 1911          }
 1912          pinfo->can_desegment=0;
 1913          pinfo->desegment_offset = 0;
 1914          pinfo->desegment_len = 0;
 1915   
 1916          if(another_pdu_follows){
 1917                  /* there was another pdu following this one. */
 1918                  pinfo->can_desegment=2;
 1919                  /* we also have to prevent the dissector from changing the
 1920                   * PROTOCOL and INFO colums since what follows may be an
 1921                   * incomplete PDU and we dont want it be changed back from 
 1922                   *  <Protocol>   to <TCP>
 1923                   * XXX There is no good way to block the PROTOCOL column 
 1924                   * from being changed yet so we set the entire row unwritable.
 1925                   */
 1926                  col_set_fence(pinfo->cinfo, COL_INFO);
 1927                  col_set_writable(pinfo->cinfo, FALSE);
 1928                  offset += another_pdu_follows;
 1929                  seq += another_pdu_follows;
 1930                  goto again;
 1931          }
 1932  }
Show more  




Change Warning 2990.33813 : Null Test After Dereference

Priority:
State:
Finding:
Owner:
Note: