/*                                              9 April 1996.  SMS.     Program to get a VAX/VMS hardware Ethernet address.*/#include <stdio.h>#include <string.h>#include <descrip.h>#include <iodef.h>#include <ssdef.h>#include <starlet.h>/*     Define: Number of Ethernet device names,             Hardware address parameter type code (no .h file), and             Size of the device characteristics buffer.*/#define  ETH_TYPES  9#define  HWA_PARAM_TYPE  1160#define  SENSE_BUF_LEN  256main(){char  *buf_ptr_byte;char  *buf_ptr_byte_end;char  *eth_name;static  char  sense_buf[ SENSE_BUF_LEN];/*     Legal Ethernet device names.  Assign any unlisted (new) device to     "ZCD$ETH_LNM" with DCL ASSIGN or DEFINE.*/char  *eth_type[ ETH_TYPES] = { "ZCD$ETH_LNM" , "ERA0:", "ESA0:", "ETA0:", "EWA0:", "EXA0:", "EZA0:",                   "XEA0:", "XQA0:"};short int  *buf_ptr_word;short int  eth_chan;short int  param_type;short int  param_type_12;int  eth_dev_index;int  i;int  ssstatus;$DESCRIPTOR( eth_name_dsc, "");/*   IOSB for QIOW.  */union   {   short int  s[ 4];   int  l[ 2];   }  iosb;/*   Descriptor for device characteristics buffer.   */struct   {   int  length;   int  *buf;   } sense_buf_dsc = { SENSE_BUF_LEN, (int*)&sense_buf };/*   Storage for the Ethernet hardware address.   */struct   {   unsigned char  byte[ 6];   } hwa = { 0, 0, 0, 0, 0, 0 };/*   Start.   *//*   Find the first available Ethernet device.   */eth_dev_index = 0;ssstatus = 0;while (!(ssstatus & 1) && (eth_dev_index < ETH_TYPES))   {   eth_name_dsc.dsc$a_pointer = eth_type[ eth_dev_index];   eth_name_dsc.dsc$w_length = strlen( eth_name_dsc.dsc$a_pointer);   ssstatus = sys$assign( &eth_name_dsc, &eth_chan, 0, 0);   eth_dev_index++;   }/*   If sys$assign worked, try to sense the characteristics.   */if (ssstatus & 1)   {   ssstatus = sys$qiow(                        0,                        eth_chan,                        (IO$_SENSEMODE | IO$M_CTRL),                        &iosb,                        0,                        0,                        0,                        &sense_buf_dsc,                        0,                        0,                        0,                        0);/*   If initial status was good, use final status.   */   if (ssstatus & 1)      {      ssstatus = iosb.s[ 0];      }/*   If sense worked, search for the hardware address field.   */   if (ssstatus & 1)      {      param_type_12 = 0;      buf_ptr_byte = (char *) &sense_buf;      buf_ptr_byte_end = (char *) &sense_buf+ SENSE_BUF_LEN;/*   Search while not found and more buffer.   */      while ((param_type_12 != HWA_PARAM_TYPE) &&       (buf_ptr_byte <= buf_ptr_byte_end))         {         buf_ptr_word = (short int *) buf_ptr_byte;         param_type = *buf_ptr_word;         param_type_12 = param_type & ((short) (1<< 12)- 1);/*     If found, store the hardware address.     Otherwise, advance the pointer to the next field.*/         if (param_type_12 == HWA_PARAM_TYPE)            {            buf_ptr_byte += 4;            for (i = 0; i < 6; i++)               {               hwa.byte[ i] = *( buf_ptr_byte++);               }            }         else if (param_type & ((short) (1<< 12)))            {/*   String field.  Skip type, length, and length-bytes.   */            buf_ptr_byte += 4+ *(buf_ptr_word+ 1);            }         else            {/*   Longword field.  Skip type and longword.   */            buf_ptr_byte += 6;            }         }      }   }   ssstatus = sys$dassgn( eth_chan);/*   Print the hardware address.   */printf( " HWA (%s) = ", eth_name_dsc.dsc$a_pointer);for (i = 0; i < 5; i++)   {   printf( "%02x-", hwa.byte[ i]);   }printf( "%02x.\n", hwa.byte[ 5]);}