#!/bin/sh

# lsvpd - Display VPD data

# This file is part of the Linux lsvpd package.

# (C) Copyright IBM Corp. 2002, 2003, 2004

# Maintained by Martin Schwenke <martins@au.ibm.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; either version 2, or (at your option)
# any later version.
 
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
 
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
    
# $Id: lsvpd.in,v 1.25 2004/06/07 05:59:39 martins Exp $

PATH="/lib/lsvpd:/sbin:${PATH}:/usr/sbin:/usr/local/sbin" ; export PATH

. "/lib/lsvpd/lsvpd-functions.bash"

shopt -s nullglob

######################################################################

do_setup ()
{
    local d i

    for d in common query lsvpd ; do
	for i in /lib/lsvpd/${d}.d/* ; do
	    . "$i"
	done
    done
}

######################################################################

usage () {
    cat <<EOF 1>&2
usage: $0 [options]
options: -h      print this usage message
         -m      Mark VPD as global or partition-private.   
         -s str  Use str as serial number.
         -t str  Use str as type/model number.
	 -d db   Directory db contains database, instead of default.
	 -z tgz  File tgz contains database archive (overrides -d).
EOF
    exit 1
}


# Options handling
mark_vpd=false
serial_num=""
type_model=""
tgz=""

options=':'
options="${options}h"
options="${options}m"
options="${options}s:"
options="${options}t:"
options="${options}d:"
options="${options}z:"
while getopts ${options} opt
do
    case ${opt}
    in
	h ) usage                ;;
	m ) mark_vpd=true        ;;
	s ) serial_num="$OPTARG" ;;
	t ) type_model="$OPTARG" ;;
        d ) db="$OPTARG"
	    if [ ! -d "$db" ] ; then
		echo "no such directory: \"${db}\"" 1>&2
		echo 1>&2
		usage
	    fi
            ;;
        z ) tgz="$OPTARG"
	    if [ ! -f "$tgz" ] ; then
		echo "no such file: \"${tgz}\"" 1>&2
		echo 1>&2
		usage
	    fi
            ;;
        \?) echo "unknown option \`${OPTARG}'" 1>&2
	    echo 1>&2
	    usage
            ;;
    esac
done
shift $((${OPTIND} - 1))

[ -n "$1" ] && usage

######################################################################

if [ -n "$tgz" ] ; then
    unpack_device_tree_archive "$tgz"
fi

######################################################################

do_setup
ensure_db

######################################################################

print_global_header ()
{
    [ -n "$serial_num" ] || serial_num=$(get_serial)
    [ -n "$type_model" ] || type_model=$(get_model)

    local os_info="unknown"

    if [ -f "${db_uname_dir}/kernel-name" -a \
	-f "${db_uname_dir}/kernel-release" ] ; then

	local name release
	read name < "${db_uname_dir}/kernel-name"
	read release < "${db_uname_dir}/kernel-release"

	os_info="${name} ${release}"
    fi

    printf "*VC 5.0\n*TM %s\n*SE %s\n*PI %s\n*OS %s\n" \
	"$type_model" "$serial_num" "$serial_num" "$os_info"
}

render_linux_vpd ()
{
    local x="$1"

    if [ -d "$x" ] ; then
	render_linux_vpd_directory "$x"
    else
	render_linux_vpd_file "$x"
    fi
}

render_linux_vpd_directory ()
{
    local d="$1"

    local vpd_subdirs
    vpd_subdirs_list_hook "${d%/linux,vpd}"
    local vpd_dir
    for vpd_dir in $vpd_subdirs ; do
	local vpd_fields
	vpd_fields_list_hook "$vpd_dir"

	local k
	for k in $vpd_fields ; do
	    local v=$(vpd_field_get "$vpd_dir" "$k")
	    if ! $mark_vpd ; then
		case "$k" in
		    (FC) v="????????" ;;
		esac
	    fi
	    echo "*${k%.*} ${v}"
	done
    done
}

render_linux_vpd_file ()
{
    local f="$1"

    if $mark_vpd ; then
	cat "$f"
    else
	sed -e 's/^\*FC .*/\*FC ????????/' "$f"
    fi
}

######################################################################

run_dynamic_vpd_hooks

print_global_header

list_linux_vpd |
while read vpd ; do
    render_linux_vpd "$vpd"
done
