Commit ecb55c3f authored by Oleg Dzhimiev's avatar Oleg Dzhimiev

added a rewritten recipe for net-tools

parent e3ca079d
#
# Makefile Main Makefile for the net-tools Package
#
# NET-TOOLS A collection of programs that form the base set of the
# NET-3 Networking Distribution for the LINUX operating
# system.
#
# Version: 2001-02-13
#
# Author: Bernd Eckenfels <net-tools@lina.inka.de>
# Copyright 1995-1996 Bernd Eckenfels, Germany
#
# URLs: ftp://ftp.inka.de/pub/comp/Linux/networking/NetTools/
# ftp://ftp.linux.org.uk/pub/linux/Networking/PROGRAMS/NetTools/
# http://www.inka.de/sites/lina/linux/NetTools/index_en.html
#
# Based on: Fred N. van Kempen, <waltje@uwalt.nl.mugnet.org>
# Copyright 1988-1993 MicroWalt Corporation
#
# Modifications:
# Extensively modified from 01/21/94 onwards by
# Alan Cox <A.Cox@swansea.ac.uk>
# Copyright 1993-1994 Swansea University Computer Society
#
# Be careful!
# This Makefile doesn't describe complete dependencies for all include files.
# If you change include files you might need to do make clean.
#
# {1.20} Bernd Eckenfels: Even more modifications for the new
# package layout
# {1.21} Bernd Eckenfels: Check if config.in is newer than
# config.status
# {1.22} Bernd Eckenfels: Include ypdomainname and nisdomainame
#
# 1.3.50-BETA6 private Release
#
#960125 {1.23} Bernd Eckenfels: Peter Tobias' rewrite for
# makefile-based installation
# 1.3.50-BETA6a private Release
#
#960201 {1.24} Bernd Eckenfels: net-features.h added
#
#960201 1.3.50-BETA6b private Release
#
#960203 1.3.50-BETA6c private Release
#
#960204 1.3.50-BETA6d private Release
#
#960204 {1.25} Bernd Eckenfels: DISTRIBUTION added
#
#960205 1.3.50-BETA6e private Release
#
#960206 {1.26} Bernd Eckenfels: afrt.o removed (cleaner solution)
#
#960215 1.3.50-BETA6f Release
#
#960216 {1.30} Bernd Eckenfels: net-lib support
#960322 {1.31} Bernd Eckenfels: moveable netlib, TOPDIR
#960424 {1.32} Bernd Eckenfels: included the URLs in the Comment
#
#960514 1.31-alpha release
#
#960518 {1.33} Bernd Eckenfels: -I/usr/src/linux/include comment added
#
# This program is free software; you can redistribute it
# and/or modify it under the terms of the GNU General
# Public License as published by the Free Software
# Foundation; either version 2 of the License, or (at
# your option) any later version.
#
# set the base of the Installation
# BASEDIR = /mnt
# path to the net-lib support library. Default: lib
NET_LIB_PATH = lib
NET_LIB_NAME = net-tools
PROGS := ifconfig hostname arp netstat route rarp slattach plipconfig nameif
-include config.make
ifeq ($(HAVE_IP_TOOLS),1)
PROGS += iptunnel ipmaddr
endif
ifeq ($(HAVE_MII),1)
PROGS += mii-tool
endif
ifeq ($(HAVE_MII_DIAG),1)
PROGS += mii-diag
endif
# Compiler and Linker Options
# You may need to uncomment and edit these if you are using libc5 and IPv6.
COPTS = -D_GNU_SOURCE -O2 -Wall -g # -I/usr/inet6/include
ifeq ($(origin LOPTS), undefined)
LOPTS =
endif
RESLIB = # -L/usr/inet6/lib -linet6
ifeq ($(HAVE_AFDECnet),1)
DNLIB = -ldnet
endif
# -------- end of user definitions --------
MAINTAINER = Philip.Blundell@pobox.com
RELEASE = 1.60
.EXPORT_ALL_VARIABLES:
ifeq ("$(NET_LIB_PATH)","lib2")
TOPDIR = ..
else
TOPDIR := $(shell if [ "$$PWD" != "" ]; then echo $$PWD; else pwd; fi)
endif
NET_LIB = $(NET_LIB_PATH)/lib$(NET_LIB_NAME).a
CFLAGS = $(COPTS) -I. -idirafter ./include/ -I$(NET_LIB_PATH)
LDFLAGS = $(LOPTS) -L$(NET_LIB_PATH)
SUBDIRS = man/ $(NET_LIB_PATH)/
ifeq ($(origin CC), undefined)
CC = gcc
endif
LD = $(CC)
NLIB = -l$(NET_LIB_NAME)
MDEFINES = COPTS='$(COPTS)' LOPTS='$(LOPTS)' TOPDIR='$(TOPDIR)'
%.o: %.c config.h version.h intl.h net-features.h $<
$(CC) $(CFLAGS) -c $<
all: config.h version.h subdirs $(PROGS)
config: cleanconfig config.h
install: all savebin installbin installdata
update: all installbin installdata
mostlyclean:
rm -f *.o DEADJOE config.new *~ *.orig lib/*.o
clean: mostlyclean
rm -f $(PROGS)
@for i in $(SUBDIRS); do (cd $$i && $(MAKE) clean) ; done
@cd po && $(MAKE) clean
cleanconfig:
rm -f config.h
clobber: clean
rm -f $(PROGS) config.h version.h config.status config.make
@for i in $(SUBDIRS); do (cd $$i && $(MAKE) clobber) ; done
dist: clobber
@echo Creating net-tools-$(RELEASE) in ..
@tar -cvz -f ../net-tools-$(RELEASE).tar.gz -C .. net-tools
config.h: config.in Makefile
@echo "Configuring the Linux net-tools (NET-3 Base Utilities)..." ; echo
@if [ config.status -nt config.in ]; \
then ./configure.sh config.status; \
else ./configure.sh config.in; \
fi
version.h: Makefile
@echo "#define RELEASE \"net-tools $(RELEASE)\"" >version.h
$(NET_LIB): config.h version.h intl.h libdir
i18n.h: i18ndir
libdir:
@$(MAKE) -C $(NET_LIB_PATH) $(MDEFINES)
i18ndir:
@$(MAKE) -C po
subdirs:
@for i in $(SUBDIRS); do $(MAKE) -C $$i $(MDEFINES) ; done
ifconfig: $(NET_LIB) ifconfig.o
$(CC) $(LDFLAGS) -o ifconfig ifconfig.o $(NLIB) $(RESLIB)
nameif: nameif.o
$(CC) $(LDFLAGS) -o nameif nameif.o
hostname: hostname.o
$(CC) $(LDFLAGS) -o hostname hostname.o $(DNLIB)
route: $(NET_LIB) route.o
$(CC) $(LDFLAGS) -o route route.o $(NLIB) $(RESLIB)
arp: $(NET_LIB) arp.o
$(CC) $(LDFLAGS) -o arp arp.o $(NLIB) $(RESLIB)
rarp: $(NET_LIB) rarp.o
$(CC) $(LDFLAGS) -o rarp rarp.o $(NLIB)
slattach: $(NET_LIB) slattach.o
$(CC) $(LDFLAGS) -o slattach slattach.o $(NLIB)
plipconfig: $(NET_LIB) plipconfig.o
$(CC) $(LDFLAGS) -o plipconfig plipconfig.o $(NLIB)
netstat: $(NET_LIB) netstat.o statistics.o
$(CC) $(LDFLAGS) -o netstat netstat.o statistics.o $(NLIB) $(RESLIB)
iptunnel: $(NET_LIB) iptunnel.o
$(CC) $(LDFLAGS) -o iptunnel iptunnel.o $(NLIB) $(RESLIB)
ipmaddr: $(NET_LIB) ipmaddr.o
$(CC) $(LDFLAGS) -o ipmaddr ipmaddr.o $(NLIB) $(RESLIB)
mii-tool: mii-tool.o
$(CC) $(LDFLAGS) -o mii-tool mii-tool.o
mii-diag: libmii.o mii-diag.o
$(CC) $(LDFLAGS) -o mii-diag libmii.o mii-diag.o
installbin:
install -m 0755 -d ${BASEDIR}/sbin
install -m 0755 -d ${BASEDIR}/bin
install -m 0755 arp ${BASEDIR}/sbin
install -m 0755 hostname ${BASEDIR}/bin
install -m 0755 ifconfig ${BASEDIR}/sbin
install -m 0755 nameif ${BASEDIR}/sbin
install -m 0755 netstat ${BASEDIR}/bin
install -m 0755 plipconfig $(BASEDIR)/sbin
install -m 0755 rarp ${BASEDIR}/sbin
install -m 0755 route ${BASEDIR}/sbin
install -m 0755 slattach $(BASEDIR)/sbin
ifeq ($(HAVE_IP_TOOLS),1)
install -m 0755 ipmaddr $(BASEDIR)/sbin
install -m 0755 iptunnel $(BASEDIR)/sbin
endif
ifeq ($(HAVE_MII),1)
install -m 0755 mii-tool $(BASEDIR)/sbin
endif
ifeq ($(HAVE_MII_DIAG),1)
install -m 0755 mii-diag $(BASEDIR)/sbin
endif
ln -fs hostname $(BASEDIR)/bin/dnsdomainname
ln -fs hostname $(BASEDIR)/bin/ypdomainname
ln -fs hostname $(BASEDIR)/bin/nisdomainname
ln -fs hostname $(BASEDIR)/bin/domainname
ifeq ($(HAVE_AFDECnet),1)
ln -fs hostname $(BASEDIR)/bin/nodename
endif
savebin:
@for i in ${BASEDIR}/sbin/arp ${BASEDIR}/sbin/ifconfig \
${BASEDIR}/bin/netstat \
${BASEDIR}/sbin/rarp ${BASEDIR}/sbin/route \
${BASEDIR}/bin/hostname ${BASEDIR}/bin/ypdomainname \
${BASEDIR}/bin/dnsdomainname ${BASEDIR}/bin/nisdomainname \
${BASEDIR}/bin/domainname ; do \
[ -f $$i ] && cp -f $$i $$i.old ; done ; echo Saved.
installdata:
$(MAKE) -C man install
$(MAKE) -C po install
# End of Makefile.
I18N=1
HAVE_AFUNIX=1
HAVE_AFINET=1
HAVE_AFINET6=1
# HAVE_AFIPX=0
# HAVE_AFATALK=0
# HAVE_AFAX25=0
HAVE_AFNETROM=1
# HAVE_AFROSE=0
# HAVE_AFX25=0
# HAVE_AFECONET=0
# HAVE_AFDECnet=0
# HAVE_AFASH=0
HAVE_HWETHER=1
HAVE_HWARC=1
HAVE_HWSLIP=1
HAVE_HWPPP=1
HAVE_HWTUNNEL=1
HAVE_HWSTRIP=1
HAVE_HWTR=1
# HAVE_HWAX25=0
# HAVE_HWROSE=0
HAVE_HWNETROM=1
# HAVE_HWX25=0
HAVE_HWFR=1
# HAVE_HWSIT=0
# HAVE_HWFDDI=0
# HAVE_HWHIPPI=0
# HAVE_HWASH=0
# HAVE_HWHDLCLAPB=0
HAVE_HWIRDA=1
# HAVE_HWEC=0
# HAVE_HWIB=0
HAVE_FW_MASQUERADE=1
HAVE_IP_TOOLS=1
HAVE_MII=1
HAVE_MII_DIAG=1
\ No newline at end of file
/* libmii.c: MII diagnostic and setup library.
Copyright 1997-2003 by Donald Becker.
This version released under the Gnu General Public License,
incorporated herein by reference.
This source code may be distributed without modification using the
existing notice. Any modification to this source code must include a
full notice as described in the GPL
Contact the author for use under other terms.
The author may be reached as becker@scyld.com, or C/O
Scyld Computing Corporation
914 Bay Ridge Road, Suite 220
Annapolis MD 21403
References
http://www.scyld.com/expert/NWay.html
http://www.national.com/pf/DP/DP83840A.html
*/
static const char version_msg[] =
"libmii.c:v2.11 2/28/2005 Donald Becker (becker@scyld.com)\n"
" http://www.scyld.com/diag/index.html\n";
/* This library exports the following functions:
IOADDR: A token passed to the mdio_read() function.
PHY_ID: The MII transceiver address, passed uninterpreted to mdio_read().
*/
void show_mii_details(long ioaddr, int phy_id);
int monitor_mii(long ioaddr, int phy_id, int opt_t, int timeout_t);
/* This library expects to be able to call the following functions: */
extern int mdio_read(long ioaddr, int phy_id, int mii_reg_num);
#include <unistd.h>
#include <stdio.h>
#include <time.h>
#include <sys/time.h>
#include <sys/types.h>
typedef u_int32_t u32;
typedef u_int16_t u16;
typedef u_int8_t u8;
static const char *media_names[] = {
"10baseT", "10baseT-FD", "100baseTx", "100baseTx-FD", "100baseT4",
"Flow-control", 0,
};
static void ns83843(long ioaddr, int phy_id);
static void qs6612(long ioaddr, int phy_id);
static void smsc83c180(long ioaddr, int phy_id);
static void tdk78q2120(long ioaddr, int phy_id);
static void davicom_dm9101(long ioaddr, int phy_id);
static void intel_i553(long ioaddr, int phy_id);
static void enablesemi(long ioaddr, int phy_id);
static void amd_pna(long ioaddr, int phy_id);
static void amd_tx(long ioaddr, int phy_id);
static void admtek(long ioaddr, int phy_id);
static void lu3x31(long ioaddr, int phy_id);
static void myson981(long ioaddr, int phy_id);
static void via_tahoe(long ioaddr, int phy_id);
static void via_vt6103(long ioaddr, int phy_id);
static void via_vt6105(long ioaddr, int phy_id);
static void intel(long ioaddr, int phy_id);
struct mii_partnum {
const char *vendor; /* Vendor name. */
u16 phy_id0; /* Vendor ID (alternate ver. of ieee_oui[]) */
u16 phy_id1; /* Vendor ID (alternate ver. of ieee_oui[]) */
unsigned char ieee_oui[3]; /* IEEE-assigned organizationally unique ID */
char flags;
void (*(func))(long xcvr_if, int phy_id);/* Function to emit more info. */
} static oui_map[] = {
{"Unknown transceiver type", 0x0000, 0x0000, {0,}, 0, NULL,},
{"National Semiconductor 83840A", 0x2000, 0x5c01, {0,}, 0, NULL,},
{"National Semiconductor 83843", 0x2000, 0x5c10, {0,}, 0, ns83843, },
{"Level One LXT970", 0x7810, 0x0000, {0,}, 0, NULL, },
{"Level One LXT971", 0x7810, 0x0001, {0,}, 0, NULL, },
{"Level One LXT971A",0x7810, 0x0003, {0,}, 0, NULL, },
{"Level One (unknown type)", 0, 0, {0x1e,0x04,0x00}, 0, NULL, },
{"Davicom DM9101", 0x0181, 0xB800, {0,}, 0, davicom_dm9101, },
{"Davicom (unknown type)", 0, 0, {0x00, 0x60, 0x6e}, 0, davicom_dm9101, },
{"Quality Semiconductor QS6612", 0x0181, 0x4410, {0,}, 0, qs6612},
{"Quality Semiconductor (unknown type)", 0,0, {0x00, 0x60, 0x51}, 0, NULL},
{"SMSC 83c180", 0x0282, 0x1C51, {0}, 0, smsc83c180, },
{"TDK Semi 78Q2120 rev. 2", 0x0300, 0xE542, {0,}, 0, tdk78q2120, },
{"TDK Semi 78Q2120 rev. 3", 0x0300, 0xE543, {0,}, 0, tdk78q2120, },
{"TDK Semi 78Q2120 rev. 11", 0x0300, 0xE54B, {0,}, 0, tdk78q2120, },
{"TDK transceiver (unknown type)", 0,0, {0x00, 0xc0, 0x39}, 0, tdk78q2120},
{"Intel (unknown type)", 0,0, {0x00, 0xf8, 0x00}, 0, intel_i553},
{"Enable Semiconductor EL40-331", 0x0043, 0x7411, {0,}, 0, enablesemi},
{"AMD 79c901A.1 HomePNA", 0x0000, 0x6B91, {0,}, 0, amd_pna},
{"AMD 79c901A.2 HomePNA", 0x0000, 0x6B92, {0,}, 0, amd_pna},
{"AMD 79c901A.3 HomePNA", 0x0000, 0x6B93, {0,}, 0, amd_pna},
{"AMD 79c901A.3 10baseT", 0x0000, 0x6B71, {0,}, 0, amd_tx},
{"AdHoc Technology AH101LF", 0x0022, 0x561B, {0,}, 0, tdk78q2120},
{"Altimata Communications AC101LF", 0x0022, 0x5523, {0,}, 0, tdk78q2120},
{"Altimata Comm (unknown type)", 0, 0, {0x00,0x10,0xA9}, 0, tdk78q2120},
{"ASIX (unknown type)", 0, 0, {0x00,0xC0,0xB4}, 0, tdk78q2120},
{"ADMtek AN983 Comet", 0x0022, 0x5410, {0,}, 0, admtek},
{"ADMtek AN985 Comet", 0x0022, 0x5513, {0,}, 0, admtek},
{"ADMtek (unknown type)", 0, 0, {0x00,0xe0,0x92}, 0, admtek},
{"Lucent LU6612", 0x0180, 0x7641, {0,}, 0, qs6612},
{"Lucent LU3X31", 0x0043, 0x7411, {0,}, 0, lu3x31},
{"LSI Logic (Seeq) 80225", 0, 0, {0x00,0xA0,0x7D}, 0, NULL},
{"Myson MTD981", 0x0302, 0xD000, {0,}, 0, myson981},
{"Myson (unknown type)", 0, 0, {0x00,0xC0,0xB4,}, 0, myson981},
{"Alta/Kendin Sundance", 0x0022, 0x1720, {0,}, 0, NULL},
{"Alta/Kendin Sundance", 0, 0, {0x00,0x08,0x85}, 0, NULL},
{"VIA Tahoe VT6103", 0x0101, 0x8f20, {0,}, 0, via_vt6103},
{"VIA Tahoe VT6104", 0x0101, 0x8f30, {0,}, 0, via_tahoe},
{"VIA Rhine VT6105", 0x0101, 0x8f22, {0,}, 0, via_vt6105},
{"Intel 82557 series", 0x02a8, 0x0150, {0,}, 0, intel},
{"Intel 82555 rev 1", 0x02a8, 0x0151, {0,}, 0, intel},
{"Intel 82559 transceiver", 0x02a8, 0x0154, {0,}, 0, intel},
{"Intel 82555 series transceiver", 0,0, {0x00,0xaa,0x00}, 0, intel},
{0, },
};
static u16 mii_val[32];
void show_mii_details(long ioaddr, int phy_id)
{
int mii_reg, i, vendor = 0;
u16 bmcr, bmsr, new_bmsr;
/* This may not be omitted from the output. */
printf("%s", version_msg);
printf(" MII PHY #%d transceiver registers:", phy_id);
for (mii_reg = 0; mii_reg < 32; mii_reg++) {
mii_val[mii_reg] = mdio_read(ioaddr, phy_id, mii_reg);
printf("%s %4.4x", (mii_reg % 8) == 0 ? "\n " : "",
mii_val[mii_reg]);
}
printf(".\n");
if (mii_val[0] == 0xffff) {
printf(" No MII transceiver present!.\n");
return;
}
bmcr = mii_val[0];
bmsr = mii_val[1];
printf(" Basic mode control register 0x%4.4x:", bmcr);
if (bmcr & 0x1000)
printf(" Auto-negotiation enabled.\n");
else
printf(" Auto-negotiation disabled!\n"
" Speed fixed at 10%s mbps, %s-duplex.\n",
bmcr & 0x2000 ? "0" : "",
bmcr & 0x0100 ? "full":"half");
if (bmcr & 0x8000)
printf(" Transceiver currently being reset!\n");
if (bmcr & 0x4000)
printf(" Transceiver in loopback mode!\n");
if (bmcr & 0x0800)
printf(" Transceiver powered down!\n");
if (bmcr & 0x0400)
printf(" Transceiver isolated from the MII!\n");
if (bmcr & 0x0200)
printf(" Restarted auto-negotiation in progress!\n");
if (bmcr & 0x0080)
printf(" Internal Collision-Test enabled!\n");
new_bmsr = mdio_read(ioaddr, phy_id, 1);
printf(" Basic mode status register 0x%4.4x ... %4.4x.\n"
" Link status: %sestablished.\n"
" Capable of ",
bmsr, new_bmsr,
bmsr & 0x0004 ? "" :
(new_bmsr & 0x0004) ? "previously broken, but now re" : "not ");
if (bmsr & 0xF800) {
for (i = 15; i >= 11; i--)
if (bmsr & (1<<i))
printf(" %s", media_names[i-11]);
} else
printf("<Warning! No media capabilities>");
printf(".\n"
" %s to perform Auto-negotiation, negotiation %scomplete.\n",
bmsr & 0x0008 ? "Able" : "Unable",
bmsr & 0x0020 ? "" : "not ");
if (bmsr & 0x0010)
printf(" Remote fault detected!\n");
if (bmsr & 0x0002)
printf(" *** Link Jabber! ***\n");
if (mii_val[2] ^ mii_val[3]) { /* Eliminate 0x0000 and 0xffff IDs. */
unsigned char oui_0 = mii_val[2] >> 10;
unsigned char oui_1 = mii_val[2] >> 2;
unsigned char oui_2 = (mii_val[2] << 6) | (mii_val[3] >> 10);
printf(" Vendor ID is %2.2x:%2.2x:%2.2x:--:--:--, model %d rev. %d.\n",
oui_0, oui_1, oui_2,
((mii_val[3] >> 4) & 0x3f), mii_val[3] & 0x0f);
for ( i = 0; oui_map[i].vendor; i++)
/* We match either the Phy ID or the IEEE OUI. */
if ((oui_map[i].phy_id0 == mii_val[2] &&
oui_map[i].phy_id1 == mii_val[3]) ||
(oui_map[i].ieee_oui[0] == oui_0 &&
oui_map[i].ieee_oui[1] == oui_1 &&
oui_map[i].ieee_oui[2] == oui_2)) {
printf(" Vendor/Part: %s.\n", oui_map[i].vendor);
vendor = i;
break;
}
if (oui_map[i].vendor == NULL)
printf(" No specific information is known about this transceiver"
" type.\n");
} else
printf(" This transceiver has no vendor identification.\n");
{
int nway_advert = mii_val[4];
int lkpar = mii_val[5];
printf(" I'm advertising %4.4x:", nway_advert);
for (i = 10; i >= 5; i--)
if (nway_advert & (1<<i))
printf(" %s", media_names[i-5]);
printf("\n Advertising %sadditional info pages.\n",
nway_advert & 0x8000 ? "" : "no ");
if ((nway_advert & 31) == 1)
printf(" IEEE 802.3 CSMA/CD protocol.\n");
else
printf(" Using an unknown (non 802.3) encapsulation.\n");
printf(" Link partner capability is %4.4x:",
lkpar);
for (i = 10; i >= 5; i--)
if (lkpar & (1<<i))
printf(" %s", media_names[i-5]);
printf(".\n Negotiation %s.\n",
lkpar & 0x4000 ? " completed" : "did not complete");
}
if (oui_map[vendor].func)
oui_map[vendor].func(ioaddr, phy_id);
}
int monitor_mii(long ioaddr, int phy_id, int opt_t, int timeout_t)
{
int i, last_event = 0,
t=timeout_t*1000; // passed as sec - make usec
unsigned short new_1, baseline_1 = mdio_read(ioaddr, phy_id, 1);
struct timeval tv, sleepval;
time_t cur_time;
char timebuf[12];
if (baseline_1 == 0xffff) {
fprintf(stderr, "No MII transceiver present to monitor.\n");
return -1;
}
gettimeofday(&tv, NULL);
cur_time = tv.tv_sec;
strftime(timebuf, sizeof(timebuf), "%H:%M:%S", localtime(&cur_time));
printf("Monitoring the MII transceiver status.\n"
"%s.%03d Baseline value of MII BMSR (basic mode status register)"
" is %4.4x.\n", timebuf, (int)tv.tv_usec/1000, baseline_1);
while (1) {
new_1 = mdio_read(ioaddr, phy_id, 1);
if (new_1 == 0xffff) {
fprintf(stderr, "The MII transceiver is no longer accessable!\n");
return -1;
}
if (new_1 != baseline_1) {
gettimeofday(&tv, NULL);
cur_time = tv.tv_sec;
strftime(timebuf, sizeof(timebuf), "%H:%M:%S",
localtime(&cur_time));
printf("%s.%03d MII BMSR now %4.4x: %4s link, NWay %s, "
"%3sJabber%s (%4.4x).\n",
timebuf, (int)tv.tv_usec/1000, new_1,
new_1 & 0x04 ? "Good" : "no",
new_1 & 0x20 ? "done" : "busy",
new_1 & 0x02 ? "" : "No ",
new_1 & 0x10 ? ", remote fault" : "",
mdio_read(ioaddr, phy_id, 5)
);
if (!(baseline_1 & 0x20) && (new_1 & 0x20)) {
int lkpar = mdio_read(ioaddr, phy_id, 5);
printf(" New link partner capability is %4.4x %4.4x:",
lkpar, mdio_read(ioaddr, phy_id, 6));
switch (lkpar) {
case 0x45e1: printf(" 10/100 switch w/ flow control"); break;
case 0x41e1: printf(" 10/100 HD+FD switch"); break;
case 0x40a1: printf(" 10/100 bridged repeater"); break;
case 0x4081: printf(" 100baseTx repeater w/autonegotation");
break;
case 0x0081: printf(" 100baseTx (no autonegotation)"); break;
case 0x4021: printf(" 10baseT repeater w/autonegotation");
break;
case 0x0021: printf(" 10baseT (no autonegotation)"); break;
default:
for (i = 9; i >= 5; i--)
if (lkpar & (1<<i))
printf(" %s", media_names[i-5]);
}
printf(".\n");
}
fflush(stdout);
baseline_1 = new_1;
last_event = 0;
}
sleepval.tv_sec = 0;
sleepval.tv_usec = last_event++ > 30 ? 200000 : 1000;
if(opt_t)
if((t-=sleepval.tv_usec/1000)<=0) break;
select(0, 0, 0, 0, &sleepval); /* Or just sleep(1); */
// sleep(1);
}
printf(" Value of MII BMSR (basic mode status register) is %4.4x.\n",
mdio_read(ioaddr, phy_id, 1));
return 0;
}
/* Emit transceiver-specific info. */
struct msg_tbl { int bitmask; char *msg; };
static void msg_if_set(const int val, const struct msg_tbl msg_tbl[])
{
int i;
for (i = 0; msg_tbl[i].bitmask; i++)
if (msg_tbl[i].bitmask & val)
printf(" %s\n", msg_tbl[i].msg);
}
static void msg_if_set_fmt(const int val, const struct msg_tbl msg_tbl[],
const char *fmt)
{
int i;
for (i = 0; msg_tbl[i].bitmask; i++)
if (msg_tbl[i].bitmask & val)
printf(fmt, msg_tbl[i].msg);
}
static void qs6612(long ioaddr, int phy_id)
{
printf(" QS6612 extra registers: Mode %4.4x.\n"
" Interrupt source %4.4x, mask %4.4x.\n"
" PHY control %4.4x.\n",
mii_val[17], mii_val[29], mii_val[30], mii_val[31]);
return;
}
static void ns83843(long ioaddr, int phy_id)
{
printf(" NatSemi 83843 extra registers:\n"
" PHY status %4.4x\n"
" %s link, %d Mb/sec %s duplex\n"
" MII interrupts %sabled, %s pending.\n"
" Events since last read\n"
" Link disconnects %d\n"
" False carriers %d\n"
" Receive errors %d\n"
" Link beat is currently %sstable\n",
mii_val[0x10],
mii_val[10] & 0x0001 ? "Valid" : "Invalid",
mii_val[10] & 0x0002 ? 10 : 100,
mii_val[10] & 0x0004 ? "full" : "half",
mii_val[0x11] & 0x0002 ? "en":"dis",
mii_val[0x10] & 0x0100 ? "interrupt": "none",
mii_val[0x13], mii_val[0x14], mii_val[0x15],
mii_val[0x16] & 0x0010 ? "UN" : "");
return;
}
static void smsc83c180(long ioaddr, int phy_id)
{
int mii_reg25 = mii_val[25];
printf(" SMSC 83c180 extra registers:\n"
" Auto-negotiation status 0x%4.4x.\n"
" 10baseT polarity is %s.\n"
" PHY address is %d.\n"
" Auto-negotiation %scomplete, 1%s0Mbps %s duplex.\n"
" Rx symbol errors since last read %d.\n",
mii_reg25,
mii_reg25 & 0x2000 ? "normal" : "reversed",
(mii_reg25>>8) & 0x1F,
mii_reg25 & 0x0080 ? "did not " : "",
mii_reg25 & 0x0020 ? "0" : "",
mii_reg25 & 0x0040 ? "full" : "half",
mdio_read(ioaddr, phy_id, 26));
return;
}
static const char *tdk_events[8] = {
"Jabber", "Rx error", "Negotiation page received", "Link detection fault",
"Link partner acknowledge", "Link status change", "Remote partner fault",
"Auto-Negotiation complete"};
static const struct msg_tbl tdk_reg16[] = {
{0x8000, " Transceiver is in repeater mode!"},
{0x4000, " Interrupt pin set to active high."},
{0x2000, " Reserved bit 12 is unexpectedly set."},
{0x1000, " Transmit pins are internally disconnected."},
{0x0800, " 10baseT signal quality test is disabled."},
{0x0400, " 10baseT loopback mode."},
{0, 0},
};
static void tdk78q2120(long ioaddr, int phy_id)
{
int mii_reg16 = mii_val[16];
int mii_reg17 = mii_val[17];
int mii_reg18 = mii_val[18];
int i;
printf(" TDK format vendor-specific registers 16..18 are "
"0x%4.4x 0x%4.4x 0x%4.4x\n", mii_reg16, mii_reg17, mii_reg18);
printf(" Link polarity is %s %s.\n"
"%s%s"
" Auto-negotiation %s, 1%s0Mbps %s duplex.\n"
" Rx link in %s state, PLL %s.\n",
mii_reg16 & 0x0020 ? "OVERRIDDEN to" : "detected as",
mii_reg16 & 0x0010 ? "reversed" : "normal",
mii_reg16 & 0x0002 ?
" 100baseTx Coding and scrambling is disabled!\n":"",
mii_reg16 & 0x0001 ? " Rx_CLK power-save mode is enabled!\n":"",
mii_reg18 & 0x1000 ? "had no common media" : "complete",
mii_reg18 & 0x0400 ? "0" : "",
mii_reg18 & 0x0800 ? "full" : "half",
mii_reg18 & 0x0200 ? "pass" : "fail",
mii_reg18 & 0x0100 ? "slipped since last read" : "locked");
msg_if_set(mii_reg16, tdk_reg16);
if (mii_reg17 & 0x00ff) {
printf(" Events since last read:");
for (i = 0; i < 8; i++)
if (mii_reg17 & (1 << i))
printf(" %s", tdk_events[i]);
} else
printf(" No new link status events.");
if (mii_reg17 & 0xff00) {
printf("\n Events that will raise an interrupt:");
for (i = 0; i < 8; i++)
if (mii_reg17 & (0x100 << i))
printf(" %s", tdk_events[i]);
}
printf("\n");
return;
}
static void davicom_dm9101(long ioaddr, int phy_id)
{
printf(" Davicom vendor specific registers: 0x%4.4x 0x%4.4x 0x%4.4x.\n",
mii_val[16], mii_val[17], mii_val[18]);
}
static void intel_i553(long ioaddr, int phy_id)
{
printf(" This transceiver is 100baseT4 only! Register 16 is %4.4x.\n",
mii_val[16]);
}
/* http://www.enablesemi.com/cgi-bin/byteserve/Products/Docs/3VCardBus.pdf */
static void enablesemi(long ioaddr, int phy_id)
{
printf(" Isolated %d times, %d false carrier events, %d Rx errors.\n",
mii_val[18], mii_val[19], mii_val[21]);
printf(" Cable polarity is %s, 100Mb PLL is %slocked.\n",
mii_val[28]&0x8000 ? "reversed" : "normal",
mii_val[27]&0x2000 ? "" : "un");
}
/* The amd79c901 contains both PNA and 10/100 management registers.
http://www.amd.com/products/npd/techdocs/22304.pdf
*/
static void amd_pna(long ioaddr, int phy_id)
{
printf(" HomePNA transceiver in %s speed, %s power mode.\n",
mii_val[16] & 4 ? "high" : "low",
mii_val[16] & 2 ? "high" : "low");
printf(" HomePNA noise level %d, peak power %d..\n",
mii_val[25] >> 8, mii_val[25] & 0xff);
}
static void amd_tx(long ioaddr, int phy_id)
{
int mii_reg25 = mii_val[25];
printf(" AMD vendor specific registers: 0x%4.4x 0x%4.4x 0x%4.4x.\n",
mii_val[16], mii_val[17], mii_val[18]);
printf(" The link is %s in 10%s %s duplex mode, autonegotiation state "
"has%s changed.\n",
mii_reg25 & 8 ? "up" : "down",
mii_reg25 & 1 ? "0baseTx" : "baseT",
mii_reg25 & 4 ? "full" : "half",
mii_reg25 & 2 ? "" : " not");
}
static const struct msg_tbl admtek_reg21[] = {
{0x4000, " Link test diabled: Ignoring lack of 10baseT link beat."},
{0x2000, " Link forced up."},
{0x1000, " Tx jabber check disabled."},
{0x0080, " Transmitting 'Far End Fault'!"},
{0x0040, " Rx error count full."},
{0x0008, " Remote loop back enabled."},
{0, 0},
};
static void admtek(long ioaddr, int phy_id)
{
printf(" ADMtek vendor specific registers information:\n"
" Cable length is approximately %d meters.\n"
" The receiver has lost lock %d times since last check and "
"had %d error events.\n",
((mii_val[20] & 0x00f0) >> 4)*10,
mii_val[23], mii_val[23]);
msg_if_set(mii_val[21], admtek_reg21);
tdk78q2120(ioaddr, phy_id);
}
static void lu3x31(long ioaddr, int phy_id)
{
printf(" Lucent vendor specific registers 17: 0x%4.4x"
" 29: 0x%4.4x 30: 0x%4.4x 31: 0x%4.4x.\n",
mii_val[17], mii_val[29], mii_val[30], mii_val[31]);
}
static const struct msg_tbl myson_reg16[] = {
{0x0080, " Far end fault enabled."},
{0x0040, " Transformer ratio 1.25:1."},
{0x0020, " Polarity correction diabled."},
{0x0010, " Link is forced up regardless of link beat."},
{0x0004, " Bypass Jabber check."},
{0x0001, " 100baseFx mode selected."},
{0, 0},
};
static void myson981(long ioaddr, int phy_id)
{
int i, mii_reg17 = mii_val[17];
printf(" Myson mtd981 extra registers: %4.4x %4.4x %4.4x %4.4x.\n",
mii_val[16], mii_val[17], mii_val[18], mii_val[19]);
msg_if_set(mii_val[16] & 0xC800, tdk_reg16);
msg_if_set(mii_val[16], myson_reg16);
if (mii_reg17 & 0x00ff) {
printf(" Events since last read:");
for (i = 0; i < 8; i++)
if (mii_reg17 & (1 << i))
printf(" %s", tdk_events[i]);
} else
printf(" No new link status events.");
if (mii_reg17 & 0xff00) {
printf("\n Events that will raise an interrupt:");
for (i = 0; i < 8; i++)
if (mii_reg17 & (0x100 << i))
printf(" %s", tdk_events[i]);
}
printf("\n");
return;
}
/* These are much like the TDK events in reversed order. */
static const struct msg_tbl via_reg17[] = {
{0x0001, "Auto-Negotiation complete"},
{0x0002, "Remote fault detected"},
{0x0004, "Link failure detected"},
{0x0008, "Bad Start Stream detected"},
{0x0010, "Parallel detection fault"},
{0x0020, "Extended negotiation page received"},
{0x0040, "5B/4B code error detected"},
{0x0080, "Jabber detected"},
{0, 0},
};
static void via_tahoe(long ioaddr, int phy_id)
{
int mii_reg16 = mii_val[16];
int mii_reg17 = mii_val[17];
int mii_reg18 = mii_val[18];
printf(" VIA Tahoe extended registers: 16 %4.4x #17 %4.4x #18 %4.4x.\n",
mii_reg16, mii_reg17, mii_reg18);
msg_if_set_fmt(mii_reg17, via_reg17, " %s\n");
printf(" Link %s 10%s Mbps %s duplex\n",
mii_reg18 & 0x2000 ? "up" : "down",
mii_reg18 & 0x0400 ? "0" : "",
mii_reg18 & 0x0800 ? "full" : "half");
}
/* Information from
http://www.via.com.tw/en/datasheet/DS6103110.pdf
*/
static void via_vt6103(long ioaddr, int phy_id)
{
printf(" VIA vt6103 error counts since the last check:\n"
" The link has failed %d times.\n"
" The receiver has lost lock %d times.\n"
" There have been %d false carrier/SQE error.\n",
mii_val[21], mii_val[22], mii_val[23]);
}
/* Information from
http://www.via.com.tw/en/Networking/DS6105LOM100.pdf
*/
static void via_vt6105(long ioaddr, int phy_id)
{
printf(" VIA vt6105 PHY status:\n"
" Duplex %s speed %s\n",
mii_val[20] & 0x0001 ? "full" : "half",
mii_val[20] & 0x0002 ? "100" : "10");
}
/* Information from
http://www.via.com.tw/en/Networking/DS6105LOM100.pdf
*/
static void intel(long ioaddr, int phy_id)
{
printf(" Intel 8255* PHY #%d extended management registers:\n"
" Error counts, cleared when read:\n"
" False carriers %d\n"
" Link disconnects %d\n"
" Receive errors %d\n"
" Rx symbol errors %d.\n"
" Rx 10Mbps Early End-Of-Frame errors %d.\n"
" Rx 100Mbps Early End-Of-Frame errors %d.\n"
" Tx jabber errors %d.\n",
mii_val[18],
mii_val[19], mii_val[20], mii_val[21], mii_val[22], mii_val[23],
mii_val[24], mii_val[25]);
}
/*
* Local variables:
* compile-command: "cc -O -Wall -c libmii.c"
* c-indent-level: 4
* c-basic-offset: 4
* tab-width: 4
* End:
*/
/* Mode: C;
* mii-diag.c: Examine and set the MII registers of a network interfaces.
Usage: mii-diag [-vw] interface.
This program reads and writes the Media Independent Interface (MII)
management registers on network transceivers. The registers control
and report network link settings and errors. Examples are link speed,
duplex, capabilities advertised to the link partner, status LED
indications and link error counters.
Notes:
The compile-command is at the end of this source file.
This program works with drivers that implement MII ioctl() calls.
Written/copyright 1997-2003 by Donald Becker <becker@scyld.com>
This program is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public
License as published by the Free Software Foundation.
The author may be reached as becker@scyld.com, or C/O
Scyld Computing Corporation
914 Bay Ridge Road, Suite 220
Annapolis MD 21403
References
http://scyld.com/expert/mii-status.html
http://scyld.com/expert/NWay.html
http://www.national.com/pf/DP/DP83840.html
*/
static char version[] =
"mii-diag.c:v2.11 3/21/2005 Donald Becker (becker@scyld.com)\n"
" http://www.scyld.com/diag/index.html\n";
static const char usage_msg[] =
"Usage: %s [--help] [-aDfrRvVw] [-t n] [-AF <speed+duplex>] [--watch] <interface>.\n";
static const char long_usage_msg[] =
"Usage: %s [-aDfrRvVw][-t <n sec>] [-AF <speed+duplex>] [--watch] <interface>.\n"
"\n"
" This program configures and monitors the transceiver management registers\n"
" for network interfaces. It uses the Media Independent Interface (MII)\n"
" standard with additional Linux-specific controls to communicate with the\n"
" underlying device driver. The MII registers control and report network\n"
" link settings and errors. Examples are link speed, duplex, capabilities\n"
" advertised to the link partner, status LED indications and link error\n"
" counters.\n"
"\n"
" The common usage is\n"
" mii-diag eth0\n"
"\n"
" The default interface is \"eth0\".\n"
" Frequently used options are\n"
" -A --advertise <speed|setting>\n"
" -F --fixed-speed <speed>\n"
" Speed is one of: 100baseT4, 100baseTx, 100baseTx-FD, 100baseTx-HD,\n"
" 10baseT, 10baseT-FD, 10baseT-HD\n"
" -s --status Return exit status 2 if there is no link beat.\n"
"\n"
" Less frequently used options are\n"
" -a --all-interfaces Show the status all interfaces\n"
" (Not recommended with options that change settings.)\n"
" -D --debug\n"
" -g --read-parameters Get driver-specific parameters.\n"
" -G --set-parameters PARMS Set driver-specific parameters.\n"
" Parameters are comma separated, missing elements retain existing value.\n"
" -M --msg-level LEVEL Set the driver message bit map.\n"
" -p --phy ADDR Set the PHY (MII address) to report.\n"
" -r --restart Restart the link autonegotiation.\n"
" -R --reset Reset the transceiver.\n"
" -v --verbose Report each action taken.\n"
" -V --version Emit version information.\n"
" -t <n> Start for n sec(by default 30 sec) and exit.\n"
" -w --watch Continuously monitor the transceiver and report changes.\n"
" MII register manipulation options are\n"
" -x --mii-addr ADDR MII register decimal address (to read, if VALUE not present). Must be in the range from '0' to '31' .\n"
" -y --mii-value VALUE write new value to MII register, hex format. Must be used together with ADDR option.\n"
"\n"
" This command returns success (zero) if the interface information can be\n"
" read. If the --status option is passed, a zero return means that the\n"
" interface has link beat.\n";
#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>
#include <ctype.h>
#include <string.h>
#include <errno.h>
#include <fcntl.h>
#include <getopt.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/ioctl.h>
#include <net/if.h>
#ifdef use_linux_libc5
#include <linux/if_arp.h>
#include <linux/if_ether.h>
#endif
typedef u_int32_t u32;
typedef u_int16_t u16;
typedef u_int8_t u8;
#if defined(SIOCGPARAMS) && SIOCGPARAMS != SIOCDEVPRIVATE+3
#error Changed definition for SIOCGPARAMS
#else
#define SIOCGPARAMS (SIOCDEVPRIVATE+3) /* Read operational parameters. */
#define SIOCSPARAMS (SIOCDEVPRIVATE+4) /* Set operational parameters. */
#endif
const char shortopts[] = "aA:C:x:y:DfF:gG:hmM:p:rRt:svVw?";
struct option longopts[] = {
/* { name has_arg *flag val } */
{"all-interfaces", 0, 0, 'a'}, /* Show all interfaces. */
{"advertise", 1, 0, 'A'}, /* Change the capabilities advertised. */
{"BMCR", 1, 0, 'C'}, /* Set the control register. */
{"debug", 0, 0, 'D'}, /* Increase the debug level. */
{"force", 0, 0, 'f'}, /* Force the operation. */
{"fixed-speed", 1, 0, 'F'}, /* Fixed speed name. */
{"read-parameters", 0, 0, 'g'}, /* Show general settings values. */
{"set-parameters", 1, 0, 'G'}, /* Write general settings values. */
{"mii-addr", 1, 0, 'x'}, /* Addr of MII register */
{"mii-value", 1, 0, 'y'}, /* value to write at MII register */
{"help", 0, 0, 'h'}, /* Print a long usage message. */
{"monitor", 0, 0, 'm'}, /* Monitor status register. */
{"msg-level", 1, 0, 'M'}, /* Set the driver message level. */
{"phy", 1, 0, 'p'}, /* Set the PHY (MII address) to report. */
{"restart", 0, 0, 'r'}, /* Restart the link negotiation */
{"reset", 0, 0, 'R'}, /* Reset the transceiver. */
{"status", 0, 0, 's'}, /* Non-zero exit status w/ no link beat. */
{"timeout", 1, 0, 't'}, /* timeout value, waiting this time and exit. */
{"verbose", 0, 0, 'v'}, /* Report each action taken. */
{"version", 0, 0, 'V'}, /* Emit version information. */
{"watch", 0, 0, 'w'}, /* Constantly monitor the port. */
{"error", 0, 0, '?'}, /* Return the error message. */
{ 0, 0, 0, 0 }
};
/* Usually in libmii.c, but trivial substitions are below. */
extern int show_mii_details(long ioaddr, int phy_id);
extern void monitor_mii(long ioaddr, int phy_id, int opt_t, int timeout_t);
int show_mii_details(long ioaddr, int phy_id) __attribute__((weak));
void monitor_mii(long ioaddr, int phy_id, int opt_t, int timeout_t) __attribute__((weak));
/* Command-line flags. */
unsigned int opt_a = 0, /* Show-all-interfaces flag. */
opt_f = 0, /* Force the operation. */
opt_g = 0,
opt_G = 0,
verbose = 0, /* Verbose flag. */
debug = 0,
opt_version = 0,
opt_restart = 0,
opt_reset = 0,
opt_status = 0,
opt_to = 0,
opt_watch = 0;
static int msg_level = -1;
static int set_BMCR = -1;
static int nway_advertise = 0;
static int fixed_speed = -1;
static int override_phy = -1;
static int timeout_t = 30;
char *opt_G_string = NULL;
#define MII_ACTION_NONE 0
#define MII_ACTION_READ 1
#define MII_ACTION_WRITE 2
static int mii_action = MII_ACTION_NONE;
unsigned mii_addr = 0xFFFF;
unsigned mii_value = 0;
int silent = 0;
/* Internal values. */
int new_ioctl_nums;
int skfd = -1; /* AF_INET socket for ioctl() calls. */
struct ifreq ifr;
int do_one_xcvr(int skfd);
int show_basic_mii(long ioaddr, int phy_id);
int mdio_read(int skfd, int phy_id, int location);
void mdio_write(int skfd, int phy_id, int location, int value);
static int parse_advertise(const char *capabilities);
static void monitor_status(long ioaddr, int phy_id);
int
main(int argc, char **argv)
{
int c, errflag = 0;
char **spp, *ifname;
char *progname = rindex(argv[0], '/') ? rindex(argv[0], '/')+1 : argv[0];
while ((c = getopt_long(argc, argv, shortopts, longopts, 0)) != EOF)
switch (c) {
case 'a': opt_a++; break;
case 'A': nway_advertise |= parse_advertise(optarg);
if (nway_advertise == -1) errflag++;
break;
case 'C': set_BMCR = strtoul(optarg, NULL, 16); break;
case 'x': {
mii_addr = strtoul(optarg, NULL, 10);
if(mii_action == MII_ACTION_NONE)
mii_action = MII_ACTION_READ;
break;
}
case 'y': {
printf("y\n");
mii_value = strtoul(optarg, NULL, 16);
mii_action = MII_ACTION_WRITE;
break;
}
case 'D': debug++; break;
case 'f': opt_f++; break;
case 'F': fixed_speed = parse_advertise(optarg);
if (fixed_speed == -1) errflag++;
break;
case 'g': opt_g++; break;
case 'G': opt_G++; opt_G_string = strdup(optarg); break;
case 'm': opt_watch++; opt_status++; break;
case 'M': msg_level = strtoul(optarg, NULL, 0); break;
case 'h': fprintf(stderr, long_usage_msg, progname); return 0;
case 'p': override_phy = atoi(optarg); break;
case 'r': opt_restart++; break;
case 'R': opt_reset++; break;
case 's': opt_status++; break;
case 't': timeout_t = strtoul(optarg, NULL, 0);
if(timeout_t<0) timeout_t=30;
opt_to++;
break;
case 'v': verbose++; break;
case 'V': opt_version++; break;
case 'w': opt_watch++; break;
case '?': errflag++; break;
}
if (errflag) {
fprintf(stderr, usage_msg, progname);
return 2;
}
if (verbose || opt_version)
printf(version);
/* Open a basic socket. */
if ((skfd = socket(AF_INET, SOCK_DGRAM,0)) < 0) {
perror("socket");
return 1;
}
if (debug)
fprintf(stderr, "DEBUG: argc=%d, optind=%d and argv[optind] is %s.\n",
argc, optind, argv[optind]);
/* No remaining args means show all interfaces. */
if (optind == argc) {
ifname = "eth0";
fprintf(stderr, "Using the default interface 'eth0'.\n");
} else {
/* Copy the interface name. */
spp = argv + optind;
ifname = *spp++;
}
if (ifname == NULL) {
ifname = "eth0";
fprintf(stderr, "Using the default interface 'eth0'.\n");
}
/* Verify that the interface supports the ioctl(), and if
it is using the new or old SIOCGMIIPHY value (grrr...).
*/
{
u16 *data = (u16 *)(&ifr.ifr_data);
strncpy(ifr.ifr_name, ifname, IFNAMSIZ);
data[0] = 0;
if (ioctl(skfd, 0x8947, &ifr) >= 0) {
new_ioctl_nums = 1;
} else if (ioctl(skfd, SIOCDEVPRIVATE, &ifr) >= 0) {
new_ioctl_nums = 0;
} else {
fprintf(stderr, "SIOCGMIIPHY on %s failed: %s\n", ifname,
strerror(errno));
(void) close(skfd);
return 1;
}
if (verbose)
printf(" Using the %s SIOCGMIIPHY value on PHY %d "
"(BMCR 0x%4.4x).\n",
new_ioctl_nums ? "new" : "old", data[0], data[3]);
}
do_one_xcvr(skfd);
(void) close(skfd);
return 0;
}
int do_one_xcvr(int skfd)
{
u16 *data = (u16 *)(&ifr.ifr_data);
u32 *data32 = (u32 *)(&ifr.ifr_data);
unsigned phy_id = data[0];
if (override_phy >= 0) {
printf("Using the specified MII PHY index %d.\n", override_phy);
phy_id = override_phy;
}
if (opt_g || opt_G || msg_level >= 0) {
if (ioctl(skfd, SIOCGPARAMS, &ifr) < 0) {
fprintf(stderr, "SIOCGPARAMS on %s failed: %s\n", ifr.ifr_name,
strerror(errno));
return -1;
}
}
if (opt_g) {
int i;
printf("Driver general parameter settings:");
for (i = 0; i*sizeof(u32) < sizeof(ifr.ifr_ifru); i++) {
printf(" %d", data32[i]);
}
printf(".\n");
}
if (opt_G) {
/* Set up to four arbitrary driver parameters from the -G parameter.
The format is comma separated integers, with a missing element
retaining the previous value.
*/
char *str = opt_G_string;
int i;
for (i = 0; str && i < 4; i++) {
char *endstr;
u32 newval = strtol(str, &endstr, 0);
if (debug)
printf(" parse string '%s' value %d end '%s'.\n",
str, newval, endstr);
if (str == endstr) {
if (endstr[0] == ',') /* No parameter */
str = endstr+1;
else {
fprintf(stderr, "Invalid driver parameter '%s'.\n", str);
str = index(str, ',');
}
} else if (endstr[0] == ',') {
data32[i] = newval;
str = endstr + 1;
} else if (endstr[0] == 0) {
data32[i] = newval;
break;
}
}
printf("Setting new driver general parameters:");
for (i = 0; i*sizeof(u32) < sizeof(ifr.ifr_ifru); i++) {
printf(" %d", data32[i]);
}
printf(".\n");
if (ioctl(skfd, SIOCSPARAMS, &ifr) < 0) {
fprintf(stderr, "SIOCSPARAMS on %s failed: %s\n", ifr.ifr_name,
strerror(errno));
return -1;
}
}
if (msg_level >= 0) {
data32[0] = msg_level;
if (ioctl(skfd, SIOCSPARAMS, &ifr) < 0) {
fprintf(stderr, "SIOCSPARAMS on %s failed: %s\n", ifr.ifr_name,
strerror(errno));
return -1;
}
}
if (opt_reset) {
printf("Resetting the transceiver...\n");
mdio_write(skfd, phy_id, 0, 0x8000);
}
/* Note: PHY addresses > 32 are pseudo-MII devices, usually built-in. */
if (phy_id < 64 && nway_advertise > 0) {
printf(" Setting the media capability advertisement register of "
"PHY #%d to 0x%4.4x.\n", phy_id, nway_advertise | 1);
mdio_write(skfd, phy_id, 4, nway_advertise | 1);
mdio_write(skfd, phy_id, 0, 0x1000);
}
if (opt_restart) {
printf("Restarting negotiation...\n");
mdio_write(skfd, phy_id, 0, 0x0000);
mdio_write(skfd, phy_id, 0, 0x1200);
}
/* To force 100baseTx-HD do mdio_write(skfd, phy_id, 0, 0x2000); */
if (fixed_speed >= 0) {
int reg0_val = 0;
if (fixed_speed & 0x0180) /* 100mpbs */
reg0_val |= 0x2000;
if ((fixed_speed & 0x0140) && /* A full duplex type and */
! (fixed_speed & 0x0820)) /* no half duplex types. */
reg0_val |= 0x0100;
printf("Setting the speed to \"fixed\", Control register %4.4x.\n",
reg0_val);
mdio_write(skfd, phy_id, 0, reg0_val);
}
if (mii_action != MII_ACTION_NONE) {
if (mii_addr > 31) {
fprintf(stderr, "MII register address must be in 0-31 diapason\n");
} else {
silent = 1;
if (mii_action == MII_ACTION_WRITE) {
mdio_write(skfd, phy_id, mii_addr, mii_value);
fprintf(stderr, "write to register MR%d value 0x%04X\n", mii_addr, mii_value);
}
if (mii_action == MII_ACTION_READ) {
unsigned long v = mdio_read(skfd, phy_id, mii_addr);
printf("0x%04X\n", v);
fprintf(stderr, "read from register MR%d value 0x%04X\n", mii_addr, v);
}
}
}
if (set_BMCR >= 0) {
printf("Setting the Basic Mode Control Register to 0x%4.4x.\n",
set_BMCR);
mdio_write(skfd, phy_id, 0, set_BMCR);
}
if (opt_watch && opt_status) {
monitor_status(skfd, phy_id);
if(opt_to) return 0;
}
show_basic_mii(skfd, phy_id);
#ifdef LIBMII
if (verbose)
show_mii_details(skfd, phy_id);
#else
if (verbose || debug) {
int mii_reg, mii_val;
printf(" MII PHY #%d transceiver registers:", phy_id);
for (mii_reg = 0; mii_reg < 32; mii_reg++) {
mii_val = mdio_read(skfd, phy_id, mii_reg);
printf("%s %4.4x", (mii_reg % 8) == 0 ? "\n " : "",
mii_val);
}
printf("\n");
}
#endif
if (opt_watch)
monitor_mii(skfd, phy_id, opt_to, timeout_t);
if (opt_status &&
(mdio_read(skfd, phy_id, 1) & 0x0004) == 0)
exit(2);
return 0;
}
int mdio_read(int skfd, int phy_id, int location)
{
u16 *data = (u16 *)(&ifr.ifr_data);
data[0] = phy_id;
data[1] = location;
if (ioctl(skfd, new_ioctl_nums ? 0x8948 : SIOCDEVPRIVATE+1, &ifr) < 0) {
fprintf(stderr, "SIOCGMIIREG on %s failed: %s\n", ifr.ifr_name,
strerror(errno));
return -1;
}
return data[3];
}
void mdio_write(int skfd, int phy_id, int location, int value)
{
u16 *data = (u16 *)(&ifr.ifr_data);
data[0] = phy_id;
data[1] = location;
data[2] = value;
if (ioctl(skfd, new_ioctl_nums ? 0x8949 : SIOCDEVPRIVATE+2, &ifr) < 0) {
fprintf(stderr, "SIOCSMIIREG on %s failed: %s\n", ifr.ifr_name,
strerror(errno));
}
}
/* Parse the command line argument for advertised capabilities. */
static int parse_advertise(const char *capabilities)
{
const char *mtypes[] = {
"100baseT4", "100baseTx", "100baseTx-FD", "100baseTx-HD",
"10baseT", "10baseT-FD", "10baseT-HD", 0,
};
char *endptr;
int cap_map[] = { 0x0200, 0x0180, 0x0100, 0x0080, 0x0060, 0x0040, 0x0020,};
int i;
if ( ! capabilities) {
fprintf(stderr, "You passed -A 'NULL'. You must provide a media"
" list to advertise!\n");
return -1;
}
if (debug)
fprintf(stderr, "Advertise string is '%s'.\n", capabilities);
for (i = 0; mtypes[i]; i++)
if (strcasecmp(mtypes[i], capabilities) == 0)
return cap_map[i];
if ((i = strtol(capabilities, &endptr, 16)) <= 0xffff && endptr[0] == 0)
return i;
fprintf(stderr, "Invalid media advertisement value '%s'.\n"
" Either pass a numeric value or one of the following names:\n",
capabilities);
for (i = 0; mtypes[i]; i++)
fprintf(stderr, " %-14s %3.3x\n", mtypes[i], cap_map[i]);
return -1;
}
/* Trivial versions if we don't link against libmii.c */
static const char *media_names[] = {
"10baseT", "10baseT-FD", "100baseTx", "100baseTx-FD", "100baseT4",
"Flow-control", 0,
};
/* Various non-good bits in the command register. */
static const char *bmcr_bits[] = {
" Internal Collision-Test enabled!\n", "", /* 0x0080,0x0100 */
" Restarted auto-negotiation in progress!\n",
" Transceiver isolated from the MII!\n",
" Transceiver powered down!\n", "", "",
" Transceiver in loopback mode!\n",
" Transceiver currently being reset!\n",
};
int show_basic_mii(long ioaddr, int phy_id)
{
int mii_reg, i;
u16 mii_val[32];
u16 bmcr, bmsr, new_bmsr, nway_advert, lkpar;
if(silent)
return 0;
for (mii_reg = 0; mii_reg < 8; mii_reg++)
mii_val[mii_reg] = mdio_read(ioaddr, phy_id, mii_reg);
if ( ! verbose) {
printf("Basic registers of MII PHY #%d: ", phy_id);
for (mii_reg = 0; mii_reg < 8; mii_reg++)
printf(" %4.4x", mii_val[mii_reg]);
printf(".\n");
}
if (mii_val[0] == 0xffff || mii_val[1] == 0x0000) {
printf(" No MII transceiver present!.\n");
if (! opt_f) {
printf(" Use '--force' to view the information anyway.\n");
return -1;
}
}
/* Descriptive rename. */
bmcr = mii_val[0];
bmsr = mii_val[1];
nway_advert = mii_val[4];
lkpar = mii_val[5];
if (lkpar & 0x4000) {
int negotiated = nway_advert & lkpar & 0x3e0;
int max_capability = 0;
/* Scan for the highest negotiated capability, highest priority
(100baseTx-FDX) to lowest (10baseT-HDX). */
int media_priority[] = {8, 9, 7, 6, 5}; /* media_names[i-5] */
printf(" The autonegotiated capability is %4.4x.\n", negotiated);
for (i = 0; media_priority[i]; i++)
if (negotiated & (1 << media_priority[i])) {
max_capability = media_priority[i];
break;
}
if (max_capability)
printf("The autonegotiated media type is %s.\n",
media_names[max_capability - 5]);
else
printf("No common media type was autonegotiated!\n"
"This is extremely unusual and typically indicates a "
"configuration error.\n" "Perhaps the advertised "
"capability set was intentionally limited.\n");
}
printf(" Basic mode control register 0x%4.4x:", bmcr);
if (bmcr & 0x1000)
printf(" Auto-negotiation enabled.\n");
else
printf(" Auto-negotiation disabled, with\n"
" Speed fixed at 10%s mbps, %s-duplex.\n",
bmcr & 0x2000 ? "0" : "",
bmcr & 0x0100 ? "full":"half");
for (i = 0; i < 9; i++)
if (bmcr & (0x0080<<i))
printf(bmcr_bits[i]);
new_bmsr = mdio_read(ioaddr, phy_id, 1);
if ((bmsr & 0x0016) == 0x0004)
printf( " You have link beat, and everything is working OK.\n");
else
printf(" Basic mode status register 0x%4.4x ... %4.4x.\n"
" Link status: %sestablished.\n",
bmsr, new_bmsr,
bmsr & 0x0004 ? "" :
(new_bmsr & 0x0004) ? "previously broken, but now re" : "not ");
if (verbose) {
printf(" This transceiver is capable of ");
if (bmsr & 0xF800) {
for (i = 15; i >= 11; i--)
if (bmsr & (1<<i))
printf(" %s", media_names[i-11]);
} else
printf("<Warning! No media capabilities>");
printf(".\n");
printf(" %s to perform Auto-negotiation, negotiation %scomplete.\n",
bmsr & 0x0008 ? "Able" : "Unable",
bmsr & 0x0020 ? "" : "not ");
}
if (bmsr & 0x0010)
printf(" Remote fault detected!\n");
if (bmsr & 0x0002)
printf(" *** Link Jabber! ***\n");
if (lkpar & 0x4000) {
printf(" Your link partner advertised %4.4x:",
lkpar);
for (i = 5; i >= 0; i--)
if (lkpar & (0x20<<i))
printf(" %s", media_names[i]);
printf("%s.\n", lkpar & 0x0400 ? ", w/ 802.3X flow control" : "");
} else if (lkpar & 0x00A0)
printf(" Your link partner is generating %s link beat (no"
" autonegotiation).\n",
lkpar & 0x0080 ? "100baseTx" : "10baseT");
else if ( ! (bmcr & 0x1000))
printf(" Link partner information is not exchanged when in"
" fixed speed mode.\n");
else if ( ! (new_bmsr & 0x004))
; /* If no partner, do not report status. */
else if (lkpar == 0x0001 || lkpar == 0x0000) {
printf(" Your link partner does not do autonegotiation, and this "
"transceiver type\n does not report the sensed link "
"speed.\n");
} else
printf(" Your link partner is strange, status %4.4x.\n", lkpar);
printf(" End of basic transceiver information.\n\n");
return 0;
}
static void monitor_status(long ioaddr, int phy_id)
{
unsigned int baseline_1 = 0x55555555; /* Always show initial status. */
int i=timeout_t;
while (1) {
unsigned int new_1 = mdio_read(ioaddr, phy_id, 1);
if (new_1 != baseline_1) {
printf("%-12s 0x%4.4x 0x%4.4x\n",
new_1 & 0x04 ? (new_1==0xffff ? "unknown" : "up") :
new_1 & 0x20 ? "negotiating" : "down",
new_1, mdio_read(ioaddr, phy_id, 5));
fflush(stdout);
baseline_1 = new_1;
}
sleep(1);
if(opt_to)
if((i--)<=0) break;
}
}
int show_mii_details(long ioaddr, int phy_id)
{
int mii_reg, mii_val;
printf(" MII PHY #%d transceiver registers:", phy_id);
for (mii_reg = 0; mii_reg < 32; mii_reg++) {
mii_val = mdio_read(skfd, phy_id, mii_reg);
printf("%s %4.4x", (mii_reg % 8) == 0 ? "\n " : "",
mii_val);
}
printf("\nThis version of 'mii-diag' has not been linked with "
"the libmii.c library.\n"
" That library provides extended transceiver status reports.\n");
return 0;
}
void monitor_mii(long ioaddr, int phy_id, int opt_t, int timeout_t)
{
fprintf(stderr, "\nThis version of 'mii-diag' has not been linked with "
"the libmii.c library \n"
" required for the media monitor option.\n");
}
/*
* Local variables:
* version-control: t
* kept-new-versions: 5
* c-indent-level: 4
* c-basic-offset: 4
* tab-width: 4
* compile-command: "gcc -Wall -Wstrict-prototypes -O mii-diag.c -DLIBMII libmii.c -o mii-diag"
* simple-compile-command: "gcc mii-diag.c -o mii-diag"
* End:
*/
/*
* config.h Automatically generated configuration includefile
*
* NET-TOOLS A collection of programs that form the base set of the
* NET-3 Networking Distribution for the LINUX operating
* system.
*
* DO NOT EDIT DIRECTLY
*
*/
/*
*
* Internationalization
*
* The net-tools package has currently been translated to French,
* German and Brazilian Portugese. Other translations are, of
* course, welcome. Answer `n' here if you have no support for
* internationalization on your system.
*
*/
#define I18N 1
/*
*
* Protocol Families.
*
*/
#define HAVE_AFUNIX 1
#define HAVE_AFINET 1
#define HAVE_AFINET6 1
#define HAVE_AFIPX 0
#define HAVE_AFATALK 0
#define HAVE_AFAX25 0
#define HAVE_AFNETROM 1
#define HAVE_AFROSE 0
#define HAVE_AFX25 0
#define HAVE_AFECONET 0
#define HAVE_AFDECnet 0
#define HAVE_AFASH 0
/*
*
* Device Hardware types.
*
*/
#define HAVE_HWETHER 1
#define HAVE_HWARC 1
#define HAVE_HWSLIP 1
#define HAVE_HWPPP 1
#define HAVE_HWTUNNEL 1
#define HAVE_HWSTRIP 0
#define HAVE_HWTR 0
#define HAVE_HWAX25 0
#define HAVE_HWROSE 0
#define HAVE_HWNETROM 1
#define HAVE_HWX25 0
#define HAVE_HWFR 1
#define HAVE_HWSIT 0
#define HAVE_HWFDDI 0
#define HAVE_HWHIPPI 0
#define HAVE_HWASH 0
#define HAVE_HWHDLCLAPB 0
#define HAVE_HWIRDA 1
#define HAVE_HWEC 0
#define HAVE_HWIB 0
/*
*
* Other Features.
*
*/
#define HAVE_FW_MASQUERADE 1
#define HAVE_IP_TOOLS 1
#define HAVE_MII 1
SUMMARY="Basic networking tools"
DESCRIPTION="A collection of programs that form the base set of the NET-3 networking distribution for the Linux operating system"
HOMEPAGE = "http://net-tools.berlios.de/"
BUGTRACKER = "http://bugs.debian.org/net-tools"
LICENSE = "GPLv2+"
LIC_FILES_CHKSUM = "file://COPYING;md5=8ca43cbc842c2336e835926c2166c28b \
file://ifconfig.c;beginline=11;endline=15;md5=d1ca372080ad5401e23ca0afc35cf9ba"
PR = "r0"
SRC_URI = "${DEBIAN_MIRROR}/main/n/net-tools/net-tools_1.60.orig.tar.gz;name=tarball \
${DEBIAN_MIRROR}/main/n/net-tools/${BPN}_${PV}.diff.gz;apply=no;name=patch \
file://net-tools-config.h"
#Notice the leading space
SRC_URI_append = " file://config.make \
file://libmii.c \
file://mii-diag.c \
file://Makefile"
S = "${WORKDIR}/net-tools-1.60"
SRC_URI[tarball.md5sum] = "ecaf37acb5b5daff4bdda77785fd916d"
SRC_URI[tarball.sha256sum] = "ec67967cf7b1a3a3828a84762fbc013ac50ee5dc9aa3095d5c591f302c2de0f5"
SRC_URI[patch.md5sum] = "524658bb8df5ff92c4a991f5edcaf240"
SRC_URI[patch.sha256sum] = "170cc024fcb34329f4c25fd88b5f160a06be5d6d3eaf0bc976650fd1b1a6235d"
inherit gettext
# The Makefile is lame, no parallel build
PARALLEL_MAKE = ""
# Unlike other Debian packages, net-tools *.diff.gz contains another series of
# patches maintained by quilt. So manually apply them before applying other local
# patches. Also remove all temp files before leaving, because do_patch() will pop
# up all previously applied patches in the start
nettools_do_patch() {
cd ${S}
quilt pop -a || true
if [ -d ${S}/.pc-nettools ]; then
mv ${S}/.pc-nettools ${S}/.pc
QUILT_PATCHES=${S}/debian/patches quilt pop -a
rm -rf ${S}/.pc ${S}/debian
fi
patch -p1 < ${WORKDIR}/${BPN}_${PV}.diff
QUILT_PATCHES=${S}/debian/patches quilt push -a
mv ${S}/.pc ${S}/.pc-nettools
}
do_unpack[cleandirs] += "${S}"
# We invoke base do_patch at end, to incorporate any local patch
python do_patch() {
bb.build.exec_func('nettools_do_patch', d)
bb.build.exec_func('patch_do_patch', d)
}
do_configure() {
# net-tools has its own config mechanism requiring "make config"
# we pre-generate desired options and copy to source directory instead
cp ${WORKDIR}/Makefile ${S}/Makefile
cp ${WORKDIR}/config.make ${S}/config.make
cp ${WORKDIR}/libmii.c ${S}/libmii.c
cp ${WORKDIR}/mii-diag.c ${S}/mii-diag.c
cp ${WORKDIR}/net-tools-config.h ${S}/config.h
}
do_compile() {
# net-tools use COPTS/LOPTS to allow adding custom options
export COPTS="$CFLAGS"
export LOPTS="$LDFLAGS"
unset CFLAGS
unset LDFLAGS
oe_runmake
}
do_install() {
oe_runmake 'BASEDIR=${D}' install
}
inherit update-alternatives
base_sbindir_progs = "arp ifconfig ipmaddr iptunnel mii-tool nameif plipconfig rarp route slattach"
base_bindir_progs = "dnsdomainname domainname hostname netstat nisdomainname ypdomainname"
ALTERNATIVE_${PN} = "${base_sbindir_progs} ${base_bindir_progs}"
python __anonymous() {
for prog in d.getVar('base_sbindir_progs', True).split():
d.setVarFlag('ALTERNATIVE_LINK_NAME', prog, '%s/%s' % (d.getVar('base_sbindir', True), prog))
for prog in d.getVar('base_bindir_progs', True).split():
d.setVarFlag('ALTERNATIVE_LINK_NAME', prog, '%s/%s' % (d.getVar('base_bindir', True), prog))
}
ALTERNATIVE_PRIORITY = "100"
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment