Example #1
0
struct lldp_tlv *create_power_via_mdi_tlv(struct lldp_port *lldp_port) {
  struct lldp_tlv* tlv = initialize_tlv();
  char OUI[3]  = {0x00, 0x01, 0x0F};
  char subtype = 2;

  if(tlv == NULL)
    return NULL;

  tlv->type = POWER_VIA_MDI_TLV;           // Constant defined in tlv_00120f.h
  tlv->length = 7; // The Power Via MDI TLV length is always 7.

  tlv->info_string = malloc(7);

  if(tlv->info_string == NULL) {
    destroy_tlv(&tlv);
    return NULL;
  }

  memcpy(tlv->info_string, OUI, 3);

  memcpy(tlv->info_string, &subtype, 1);

  // Are there any devices in *NIX that support PSE or PD as per RFC 3621?
 
  return tlv;  
}
Example #2
0
// MAC/PHY Configuration/Status TLV
struct lldp_tlv *create_mac_phy_configuration_status_tlv(struct lldp_port *lldp_port) {
  struct lldp_tlv *tlv = initialize_tlv();
  char OUI[3]  = {0x00, 0x01, 0x0F};
  char subtype = 1;

  if(tlv == NULL)
    return NULL;

  tlv->type = MAC_PHY_CONFIGURATION_STATUS_TLV; // Constant defined in tlv_00120f.h
  tlv->length = 9;                       // The MAC/PHY Configuration/Status TLV length is always 9.

  tlv->info_string = malloc(9);

  if(tlv->info_string == NULL) {
    destroy_tlv(&tlv);
    return NULL;
  }

  memcpy(&tlv->info_string[0], OUI, 3);

  memcpy(&tlv->info_string[3], &subtype, 1);
  /*
  memcpy(&tlv->info_string[4], &lldp_port->autoNegCapabilitiesAndSupport, 1);

  memcpy(&tlv->info_string[5], &lldp_port->ifMauAutoNegCapAdvertisedBits, 2);
  
  memcpy(&tlv->info_string[7], &lldp_port->ifMauType, 2);
  */ 

  return tlv;  
}
Example #3
0
struct lldp_tlv *create_end_of_lldpdu_tlv(struct lldp_port *lldp_port) {

    struct lldp_tlv* tlv = initialize_tlv();

    tlv->type = END_OF_LLDPDU_TLV; // Constant defined in lldp_tlv.h
    tlv->length = 0;     // The End of LLDPDU TLV is length 0.

    tlv->info_string = NULL;

    return tlv;
}
Example #4
0
// NB: Initial deployment will do IPv4 only... 
// 
struct lldp_tlv *create_management_address_tlv(struct lldp_port *lldp_port) {
   struct lldp_tlv *tlv = initialize_tlv();
   uint32_t if_index = htonl(lldp_port->if_index);

    tlv->type = MANAGEMENT_ADDRESS_TLV; // Constant defined in lldp_tlv.h

#define MGMT_ADDR_STR_LEN 1
#define MGMT_ADDR_SUBTYPE 1
#define IPV4_LEN 4
#define IF_NUM_SUBTYPE 1
#define IF_NUM 4
#define OID 1
#define OBJ_IDENTIFIER 0

    // management address string length (1 octet)
    // management address subtype (1 octet)
    // management address (4 bytes for IPv4)
    // interface numbering subtype (1 octet)
    // interface number (4 bytes)
    // OID string length (1 byte)
    // object identifier (0 to 128 octets)
    tlv->length = MGMT_ADDR_STR_LEN + MGMT_ADDR_SUBTYPE + IPV4_LEN + IF_NUM_SUBTYPE + IF_NUM + OID + OBJ_IDENTIFIER ;

    //uint64_t tlv_offset = 0;

    tlv->info_string = calloc(1, tlv->length);

    // Management address string length
    // subtype of 1 byte + management address length, so 5 for IPv4
    tlv->info_string[0] = 5;

    // 1 for IPv4 as per http://www.iana.org/assignments/address-family-numbers
    tlv->info_string[1] = 1;

    // Copy in our IP
    memcpy(&tlv->info_string[2], lldp_port->source_ipaddr, 4);

    // Interface numbering subtype... system port number in our case.
    tlv->info_string[6] = 3;

    // Interface number... 4 bytes long, or uint32_t
    memcpy(&tlv->info_string[7], &lldp_port->if_index, sizeof(uint32_t));

    debug_printf(DEBUG_NORMAL, "Would stuff interface #: %d\n", if_index);

    // OID - 0 for us
    tlv->info_string[11] = 0;

    // object identifier... doesn't exist for us because it's not required, and we don't have an OID.

    return tlv;
}
Example #5
0
struct lldp_tlv *create_system_name_tlv(struct lldp_port *lldp_port) 
{

    struct lldp_tlv* tlv = initialize_tlv();

    tlv->type = SYSTEM_NAME_TLV; // Constant defined in lldp_tlv.h
    tlv->length = strlen(lldp_systemname);

    tlv->info_string = calloc(1, tlv->length);

    memcpy(tlv->info_string, lldp_systemname, tlv->length); 

    return tlv;
}
Example #6
0
struct lldp_tlv *create_port_description_tlv(struct lldp_port *lldp_port) {

    struct lldp_tlv* tlv = initialize_tlv();

    tlv->type = PORT_DESCRIPTION_TLV; // onstant defined in lldp_tlv.h
    tlv->length = strlen(lldp_port->if_name);

    tlv->info_string = calloc(1, tlv->length);

    memcpy(&tlv->info_string[0], lldp_port->if_name, strlen(lldp_port->if_name));

    return tlv;

}
Example #7
0
struct lldp_tlv *create_ttl_tlv(struct lldp_port *lldp_port) {

    struct lldp_tlv* tlv = initialize_tlv();
    uint16_t ttl = htons(lldp_port->tx.txTTL);

    tlv->type = TIME_TO_LIVE_TLV; // Constant defined in lldp_tlv.h
    tlv->length = 2; // Static length defined by IEEE 802.1AB section 9.5.4

    tlv->info_string = calloc(1, tlv->length);

    memcpy(tlv->info_string, &ttl, tlv->length);

    return tlv;
}
Example #8
0
struct lldp_tlv *create_system_capabilities_tlv(struct lldp_port *lldp_port) {
    struct lldp_tlv* tlv = initialize_tlv();
    // Tell it we're a station for now... bit 7
    uint16_t capabilities = htons(128);

    tlv->type = SYSTEM_CAPABILITIES_TLV; // Constant defined in lldp_tlv.h

    tlv->length = 4;

    tlv->info_string = calloc(1, tlv->length);

    memcpy(&tlv->info_string[0], &capabilities, sizeof(uint16_t));
    memcpy(&tlv->info_string[2], &capabilities, sizeof(uint16_t));

    return tlv;
}
Example #9
0
struct lldp_tlv *create_system_description_tlv(struct lldp_port *lldp_port)
{

    struct lldp_tlv* tlv = initialize_tlv();

    tlv->type = SYSTEM_DESCRIPTION_TLV; // Constant defined in lldp_tlv.h

    tlv->length = strlen(lldp_systemdesc);

    tlv->info_string = calloc(1, tlv->length);

    memcpy(tlv->info_string, lldp_systemdesc, tlv->length);

    return tlv;

}
Example #10
0
struct lldp_tlv *create_chassis_id_tlv(struct lldp_port *lldp_port) {

    struct lldp_tlv* tlv = initialize_tlv();

    tlv->type = CHASSIS_ID_TLV; // Constant defined in lldp_tlv.h
    tlv->length = 7; //The size of a MAC + the size of the subtype (1 byte)

    tlv->info_string = calloc(1, tlv->length);  

    // CHASSIS_ID_MAC_ADDRESS is a 1-byte value - 4 in this case. Defined in lldp_tlv.h
    tlv->info_string[0] = CHASSIS_ID_MAC_ADDRESS;

    // We need to start copying at the 2nd byte, so we use [1] here...
    // This reads "memory copy to the destination at the address of tlv->info_string[1] with the source my_mac for 6 bytes" (the size of a MAC address)
    memcpy(&tlv->info_string[1], &lldp_port->source_mac[0], 6);

    return tlv;
}
Example #11
0
struct lldp_tlv *create_port_id_tlv(struct lldp_port *lldp_port) {

    struct lldp_tlv* tlv = initialize_tlv();

    tlv->type = PORT_ID_TLV; // Constant defined in lldp_tlv.h
    tlv->length = 1 + strlen(lldp_port->if_name); //The length of the interface name + the size of the subtype (1 byte)

    tlv->info_string = calloc(1, tlv->length);

    // PORT_ID_INTERFACE_NAME is a 1-byte value - 5 in this case. Defined in lldp_tlv.h
    tlv->info_string[0] = PORT_ID_INTERFACE_NAME;


    // We need to start copying at the 2nd byte, so we use [1] here...
    // This reads "memory copy to the destination at the address of tlv->info_string[1] with the source lldp_port->if_name for strlen(lldp_port->if_name) bytes"
    memcpy(&tlv->info_string[1], lldp_port->if_name, strlen(lldp_port->if_name));

    return tlv;
}
Example #12
0
struct lldp_tlv *create_lldpmed_location_identification_tlv (struct lldp_port *lldp_port)
{
  int j;  
  int len = 0;
  int pos = 0;
  struct lldp_tlv *tlv = initialize_tlv();


  //just 1, 2 or 3 is allowed for location data format, 0 is invalid, 4-255 is reserved for future use
  if ((lci.location_data_format < 1) || (lci.location_data_format > 3))
    {
      debug_printf (DEBUG_NORMAL, "[ERROR] in config file: invalid location_data_format '%d' \n", lci.location_data_format);

      free(tlv);

      return NULL;
    }

  //set CATypes with no content "" to NULL, otherwise CAType with length 0 is created
  for (j = 0; j < 33; j++)
    {
      if ((lci.civic_ca[j] != NULL) && (strcmp (lci.civic_ca[j], "") == 0))
	lci.civic_ca[j] = NULL;
    }
  
  //calculate LCI Length for Civic Location
  if (lci.location_data_format == LCI_CIVIC)
    {
      for (j = 0; j < 33; j++)
	{
	  //printf ("%i\n", j);
	  //(strlen(civic_ca[j]) > 0) &&
	  if ((lci.civic_ca[j] != NULL))
	    len += strlen (lci.civic_ca[j]) + 1 + 1;//length of CAvalue + CAtype + CAlength
	}
      len += 1 + 2;//add len for What and Countrycode
      tlv->length = 1 + len + 4 + 1;//1 for the LCI length field, LCI length plus 4 for the MED Header and 1 for Location Data Format
    }
  
  //length for coordinate based
  if (lci.location_data_format == LCI_COORDINATE)
    {
      int tmp = strlen (lci.coordinate_based_lci) / 2;
      if (tmp == 23)
	debug_printf (DEBUG_NORMAL, "Coordinate based LCI contains colons\n");
      
      if ((tmp != 16) && (tmp != 23))
	debug_printf (DEBUG_NORMAL, "coordinate_based_lci has wrong length '%d' \n", tmp);
      
      tlv->length = 16 + 5;//MED Header (5) + geo location is always 16
      //printf ("geo loc data length calculated = %i \n", tlv->length);
    }
  
  //length for ELIN
  if (lci.location_data_format == LCI_ELIN)
    tlv->length = strlen (lci.elin) + 5;
  
  tlv->type = ORG_SPECIFIC_TLV;
  
  tlv->info_string = calloc(1, tlv->length);
  
  //MED-Header
  tlv->info_string[0] = 0x00;
  tlv->info_string[1] = 0x12;
  tlv->info_string[2] = 0xBB;
  tlv->info_string[3] = 3;
  
  //set Location Data Format
  tlv->info_string[4] = lci.location_data_format;
  
  
  //--------------------
  // create Location ID
  //--------------------

  //handle civic location LCI
  if (lci.location_data_format == 2)
    {
      tlv->info_string[5] = len;//LCI Length
      tlv->info_string[6] = lci.civic_what;
      tlv->info_string[7] = lci.civic_countrycode[0];
      tlv->info_string[8] = lci.civic_countrycode[1];
      pos = 9;
      
      debug_printf (DEBUG_NORMAL, "create civic location identification TLV\n");
      //for(j = 0; j < 33; j++)
      //printf("CA typ %i len(%i) = %s \n", j, strlen(civic_ca[j]), civic_ca[j]);
      //printf("nr 12 %s",civic_ca[12]);
      
      for (j = 0; j < 33; j++)
	{
	  //(strlen(civic_ca[j]) > 1) &&
	  if ((lci.civic_ca[j] != NULL))
	    {
	      int calength = strlen (lci.civic_ca[j]);
	      debug_printf (DEBUG_NORMAL, "CA Type %i with len %i contains %s \n", j,
			    calength, lci.civic_ca[j]);
	      tlv->info_string[pos] = j;
	      pos++;
	      tlv->info_string[pos] = calength;
	      pos++;
	      memcpy(&tlv->info_string[pos], lci.civic_ca[j], calength);
	      pos += calength;
	    }
	}
       }
  
  //handle ECS ELIN data format
  if (lci.location_data_format == 3)
    memcpy(&tlv->info_string[5], lci.elin, strlen(lci.elin));
  
  //handling coordinate-based LCI
  if (lci.location_data_format == 1)
    {
      char temp[3];
      char out[17]; // binary location + string terminator
      char *in = calloc (1, strlen(lci.coordinate_based_lci) + 1);
      int k, i, u;
      int counter = 0;
      //remove colons from string
      for (u = 0; u < strlen (lci.coordinate_based_lci); u++)
	{
	  if (lci.coordinate_based_lci[u] != ':')
	    {
	      in[counter] = lci.coordinate_based_lci[u];
	      counter++;
	    }
	}
      
      in[32] = '\0'; // initialize string terminators
      out[16] = '\0';
      temp[2] = '\0'; 
      
            debug_printf (DEBUG_NORMAL, "coordinate_based_lci: %s\n", lci.coordinate_based_lci);
	    debug_printf (DEBUG_NORMAL, "coordinate_based without colons: %s \n", in);
	    
	    //convert string to hex
	    for (i = 0; i < 16; i++)
	      {
		temp[0] = in[i * 2];
		temp[1] = in[i * 2 + 1];
		out[i] = (char) strtol (temp, NULL, 16);
	      }
	    
	    free (in);
	    
	    debug_printf (DEBUG_NORMAL, "out: ");
	    for (i = 0; i < 16; i++)
	      {
		//proper output requires unsigned char cast
	        debug_printf (DEBUG_NORMAL, "%02x", (unsigned char)out[i]);
	      }
	    debug_printf (DEBUG_NORMAL, "\n");
	    
	    memcpy(&tlv->info_string[5], out, 16);
    }
  
  return tlv;
}