⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 _corba.c

📁 This directory contains source code for tcpdump, a tool for network monitoring and data acquisition
💻 C
📖 第 1 页 / 共 2 页
字号:
/*
 *
 *   BBN Technologies
 *   10 Moulton St.
 *   Cambridge, MA 02138
 *   (617) 873-2000
 *
 *   Copyright (C) 1998, 1999
 *   This software is subject to copyright protection under the laws of
 *   the United States and other countries.
 *
 *  Redistribution and use in source and binary forms, with or without
 *  modification, are permitted provided that: (1) source code
 *  distributions retain the above copyright notice and this paragraph
 *  in its entirety, (2) distributions including binary code include
 *  the above copyright notice and this paragraph in its entirety in
 *  the documentation or other materials provided with the
 *  distribution, and (3) all advertising materials mentioning features
 *  or use of this software display the following acknowledgement:
 *  ``This product includes software developed by the BBN Technologies
 *  and its contributors.'' Neither the name of t BBN nor the names of
 *  its contributors may be used to endorse or promote products derived
 *  from this software without specific prior written permission.  THIS
 *  SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
 *  WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES
 *  OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
 *
 */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include <sys/param.h>
#include <sys/time.h>

#include <netinet/in.h>
#include <netinet/in_systm.h>
#include <netinet/ip.h>
#include <netinet/ip_var.h>
#include <netinet/tcp.h>
#include <netinet/tcpip.h>

#include "interfac.h"
#include "a2name.h"
#include "extract.h"
#include "giop.h"


#ifndef timeradd
#define timeradd(a, b, result)   \
  do {      \
    (result)->tv_sec = (a)->tv_sec + (b)->tv_sec;                           \
    (result)->tv_usec = (a)->tv_usec + (b)->tv_usec;                        \
    if ((result)->tv_usec >= 1000000)                                       \
      {   \
      ++(result)->tv_sec;                                                   \
      (result)->tv_usec -= 1000000;                                         \
      }  \
  } while (0)

#endif

#ifndef timersub
#define timersub(a, b, result)  \
  do {  \
    (result)->tv_sec = (a)->tv_sec - (b)->tv_sec;                           \
    (result)->tv_usec = (a)->tv_usec - (b)->tv_usec;                        \
    if ((result)->tv_usec < 0) {                                            \
      --(result)->tv_sec;                                                   \
      (result)->tv_usec += 1000000;                                         \
    }                                                                       \
  } while (0)
#endif


/*
 * The entries below are per 'stream', not per conversation
 * The src host, src port, dst host and dst port must all
 * match.
 */
struct iiop_tha {
       struct in_addr src;
       struct in_addr dst;
       u_short        src_port;
       u_short        dst_port;
     };

struct iiop_msg {
       struct iiop_msg  *nxt;
       struct timeval    first;
       struct timeval    last;
       struct iiop_tha   addr;
       struct MessageHeader_1_x *hdr;
     };

struct iiop_stream {
       struct iiop_stream *nxt;
       struct iiop_tha     addr;

       /* List of iiop messages for this stream */
       struct iiop_msg *msg;

       /* State of the current message for this stream */
       u_int size;
       u_int seq;
       u_int consumed;
     };

static struct iiop_msg    *requests;
static struct iiop_stream *iiop_streams = NULL;

static __inline u_int iiop_size (const struct MessageHeader_1_x *header)
{
  u_int32_t message_size = header->messageSize;

  return gtohl (message_size, header->flags);
}

static __inline u_int32_t giop_reply_id (const struct MessageHeader_1_x *header)
{
  const struct Sequence    *seq = (struct Sequence*) &header->payload;
  const struct ReplyHeader *repHeader;
  u_char *data = (u_char*) &seq->payload;
  int     i;

  for (i = 0; i < seq->numElements; i++)
     data = skip_context (data);

  repHeader = (struct ReplyHeader*) data;
  return (repHeader->request_id);
}

static __inline u_int32_t giop_request_id (const struct MessageHeader_1_x *header)
{
  const struct Sequence          *seq = (struct Sequence*) &header->payload;
  const struct RequestHeader_1_0 *reqHeader_1_0;
  const struct RequestHeader_1_1 *reqHeader_1_1;
  u_char *data = (u_char*) &seq->payload;
  int     version = header->GIOPVersion.major << 8 | header->GIOPVersion.minor;
  int     i;

  for (i = 0; i < seq->numElements; i++)
     data = skip_context (data);

  switch (version)
  {
    case 0x0100:            /* 1.0 */
         reqHeader_1_0 = (struct RequestHeader_1_0 *) (data);
         return (reqHeader_1_0->request_id);

    case 0x0101:            /* 1.1 */
         reqHeader_1_1 = (struct RequestHeader_1_1 *) (data);
         return (reqHeader_1_1->request_id);
  } 
  return (-1);
}

static __inline int is_oneway (const struct MessageHeader_1_x *header)
{
  const struct Sequence          *seq = (struct Sequence*) &header->payload;
  const struct RequestHeader_1_0 *reqHeader_1_0;
  const struct RequestHeader_1_1 *reqHeader_1_1;
  u_char *data = (u_char*) &seq->payload;
  int    version = header->GIOPVersion.major << 8 | header->GIOPVersion.minor;
  int    i;

  for (i = 0; i < seq->numElements; i++)
     data = skip_context (data);

  switch (version)
  {
    case 0x0100:            /* 1.0 */
         reqHeader_1_0 = (struct RequestHeader_1_0*) data;
         return (!reqHeader_1_0->response_expected);

    case 0x0101:            /* 1.1 */
         reqHeader_1_1 = (struct RequestHeader_1_1*) data;
         return (!reqHeader_1_1->response_expected);
  }
  return (0);
}

static void print_iiop_message (const struct MessageHeader_1_x *header)
{
  const struct Sequence          *seq = (struct Sequence*) &header->payload;
  const struct RequestHeader_1_0 *reqHeader_1_0;
  const struct RequestHeader_1_1 *reqHeader_1_1;
  const OctetSequence            *octetSeq = NULL;
  u_char *data = (u_char*) &seq->payload;
  int     version = header->GIOPVersion.major << 8 | header->GIOPVersion.minor;
  int     i;

  for (i = 0; i < seq->numElements; i++)
     data = skip_context (data);

  switch (version)
  {
    case 0x0100:            /* 1.0 */
         reqHeader_1_0 = (struct RequestHeader_1_0*) data;
         data = print_object_key (reqHeader_1_0->object_key._length,
                                  (u_char*) &reqHeader_1_0->object_key._buffer);
         octetSeq = (OctetSequence*) data; /* Should be String, but... */
         break;

    case 0x0101:            /* 1.1 */
         reqHeader_1_1 = (struct RequestHeader_1_1*) data;
         data = print_object_key (reqHeader_1_1->object_key._length,
                                  (u_char*) &reqHeader_1_1->object_key._buffer);
         octetSeq = (OctetSequence*) data; /* Should be String, but... */
         break;

    default:
         PRINTF ("version %d?", version);
         return;
  }
  PRINTF ("\"%s\" ", &octetSeq->_buffer); /* Already null terminated */

}

static void ts_diff_print (const struct timeval *tvp1, const struct timeval *tvp2)
{
  struct timeval diff;
  struct timeval *tvp = &diff;

  timersub (tvp1, tvp2, tvp);

  /* ts_print accomodates for timezone, so adjust here too
   */
  tvp->tv_sec -= thiszone;
  ts_print (tvp);
}


static void free_msg (struct iiop_msg *msg)
{
  free (msg->hdr);
  free (msg);
}


static void free_request (struct iiop_msg *request)
{
  if (request == requests)
     requests = request->nxt;
  else
  {
    struct iiop_msg *prev = requests;
    struct iiop_msg *req  = requests->nxt;

    while (req)
    {
      if (req == request)
      {
        prev->nxt = req->nxt;
        break;
      }
      prev = req;
      req = req->nxt;
    }
  }
  free_msg (request);
}

static void print_corba_call (struct iiop_msg *request,
                              struct iiop_msg *reply,
                              struct timeval  *reply_first,
                              struct timeval  *reply_last)
{
  struct MessageHeader_1_x *hdr = request->hdr;
  int    id     = giop_request_id (hdr);
  int    length = hdr->messageSize;

  /* Length needs to be incremented by the reply length
   */
  if (reply)
     length += reply->hdr->messageSize;

  PUTCHAR ('\n');
  if (reply)
       ts_print (reply_last);
  else ts_print (&request->last);

  PRINTF ("%s.%d > %s.%d: Corba %d.%d %d ",
          ipaddr_string (&request->addr.src), request->addr.src_port,
          ipaddr_string (&request->addr.dst), request->addr.dst_port,
          hdr->GIOPVersion.major, hdr->GIOPVersion.minor, length);

  if (reply)
       PRINTF ("Call %d ", id);
  else PRINTF ("Oneway %d ", id);

  print_iiop_message (request->hdr);

  /* Call-duration
   */
  if (reply)
       ts_diff_print (reply_last, &request->first);
  else ts_diff_print (&request->last, &request->first);

  if (reply)
  {
    /* request-length, reply-length, request-duration, reply-duration
     * Server-duration
      */
    PRINTF ("%d %d ", hdr->messageSize, reply->hdr->messageSize);
    ts_diff_print (&request->last, &request->first);
    ts_diff_print (reply_last, reply_first);
    ts_diff_print (reply_first, &request->last);
  }
  else
  {
    /* request-length, NA, request-duration, NA, NA
     */
    PRINTF ("%d NA ", hdr->messageSize);
    ts_diff_print (&request->last, &request->first);
    PUTS ("NA NA");
  }
  free_request (request);
}


static void print_unmatched_corba_request (struct iiop_msg *request)
{
  struct MessageHeader_1_x *hdr = request->hdr;
  int    id     = giop_request_id (hdr);
  int    length = hdr->messageSize;

  PUTCHAR ('\n');
  ts_print (&request->last);
  PRINTF ("%s.%d > %s.%d: Corba %d.%d ",
          ipaddr_string (&request->addr.src), request->addr.src_port,
          ipaddr_string (&request->addr.dst), request->addr.dst_port,
          hdr->GIOPVersion.major, hdr->GIOPVersion.minor);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -