xref: /onnv-gate/usr/src/cmd/sgs/libconv/common/cap.c (revision 11734:d29dc9c2b6c5)
10Sstevel@tonic-gate /*
20Sstevel@tonic-gate  * CDDL HEADER START
30Sstevel@tonic-gate  *
40Sstevel@tonic-gate  * The contents of this file are subject to the terms of the
51618Srie  * Common Development and Distribution License (the "License").
61618Srie  * You may not use this file except in compliance with the License.
70Sstevel@tonic-gate  *
80Sstevel@tonic-gate  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
90Sstevel@tonic-gate  * or http://www.opensolaris.org/os/licensing.
100Sstevel@tonic-gate  * See the License for the specific language governing permissions
110Sstevel@tonic-gate  * and limitations under the License.
120Sstevel@tonic-gate  *
130Sstevel@tonic-gate  * When distributing Covered Code, include this CDDL HEADER in each
140Sstevel@tonic-gate  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
150Sstevel@tonic-gate  * If applicable, add the following below this CDDL HEADER, with the
160Sstevel@tonic-gate  * fields enclosed by brackets "[]" replaced with your own identifying
170Sstevel@tonic-gate  * information: Portions Copyright [yyyy] [name of copyright owner]
180Sstevel@tonic-gate  *
190Sstevel@tonic-gate  * CDDL HEADER END
200Sstevel@tonic-gate  */
211618Srie 
220Sstevel@tonic-gate /*
23*11734SAli.Bahrami@Sun.COM  * Copyright 2010 Sun Microsystems, Inc.  All rights reserved.
240Sstevel@tonic-gate  * Use is subject to license terms.
250Sstevel@tonic-gate  */
260Sstevel@tonic-gate 
270Sstevel@tonic-gate /*
280Sstevel@tonic-gate  * String conversion routine for hardware capabilities types.
290Sstevel@tonic-gate  */
300Sstevel@tonic-gate #include	<strings.h>
310Sstevel@tonic-gate #include	<stdio.h>
320Sstevel@tonic-gate #include	<elfcap.h>
331976Sab196087 #include	"cap_msg.h"
340Sstevel@tonic-gate #include	"_conv.h"
350Sstevel@tonic-gate 
369273SAli.Bahrami@Sun.COM const conv_ds_t **
379273SAli.Bahrami@Sun.COM conv_cap_tag_strings(Conv_fmt_flags_t fmt_flags)
380Sstevel@tonic-gate {
39*11734SAli.Bahrami@Sun.COM #if	(CA_SUNW_NUM != (CA_SUNW_HW_2 + 1))
40*11734SAli.Bahrami@Sun.COM #error	"CA_SUNW_NUM has grown"
41*11734SAli.Bahrami@Sun.COM #endif
429273SAli.Bahrami@Sun.COM 	static const Msg	tags_cf[] = {
439273SAli.Bahrami@Sun.COM 		MSG_CA_SUNW_NULL_CF,	MSG_CA_SUNW_HW_1_CF,
44*11734SAli.Bahrami@Sun.COM 		MSG_CA_SUNW_SF_1_CF,	MSG_CA_SUNW_HW_2_CF
459273SAli.Bahrami@Sun.COM 	};
469273SAli.Bahrami@Sun.COM 	static const Msg	tags_nf[] = {
479273SAli.Bahrami@Sun.COM 		MSG_CA_SUNW_NULL_NF,	MSG_CA_SUNW_HW_1_NF,
48*11734SAli.Bahrami@Sun.COM 		MSG_CA_SUNW_SF_1_NF,	MSG_CA_SUNW_HW_2_NF,
499273SAli.Bahrami@Sun.COM 	};
509273SAli.Bahrami@Sun.COM 	static const conv_ds_msg_t ds_tags_cf = {
519273SAli.Bahrami@Sun.COM 	    CONV_DS_MSG_INIT(ELFCLASSNONE, tags_cf) };
529273SAli.Bahrami@Sun.COM 	static const conv_ds_msg_t ds_tags_nf = {
539273SAli.Bahrami@Sun.COM 	    CONV_DS_MSG_INIT(ELFCLASSNONE, tags_nf) };
545088Sab196087 
559273SAli.Bahrami@Sun.COM 	static const conv_ds_t *ds_cf[] = { CONV_DS_ADDR(ds_tags_cf), NULL };
569273SAli.Bahrami@Sun.COM 	static const conv_ds_t *ds_nf[] = { CONV_DS_ADDR(ds_tags_nf), NULL };
570Sstevel@tonic-gate 
580Sstevel@tonic-gate 
599273SAli.Bahrami@Sun.COM 	return ((CONV_TYPE_FMT_ALT(fmt_flags) == CONV_FMT_ALT_NF) ?
609273SAli.Bahrami@Sun.COM 	    ds_nf : ds_cf);
619273SAli.Bahrami@Sun.COM }
629273SAli.Bahrami@Sun.COM 
639273SAli.Bahrami@Sun.COM conv_iter_ret_t
649273SAli.Bahrami@Sun.COM conv_iter_cap_tags(Conv_fmt_flags_t fmt_flags, conv_iter_cb_t func,
659273SAli.Bahrami@Sun.COM     void *uvalue)
669273SAli.Bahrami@Sun.COM {
679273SAli.Bahrami@Sun.COM 	return (conv_iter_ds(ELFOSABI_NONE, EM_NONE,
689273SAli.Bahrami@Sun.COM 	    conv_cap_tag_strings(fmt_flags), func, uvalue));
690Sstevel@tonic-gate }
700Sstevel@tonic-gate 
719273SAli.Bahrami@Sun.COM /*
729273SAli.Bahrami@Sun.COM  * Given an array of elfcap_desc_t, and a count, call the specified
739273SAli.Bahrami@Sun.COM  * iteration for each value in the array.
749273SAli.Bahrami@Sun.COM  */
759273SAli.Bahrami@Sun.COM static conv_iter_ret_t
769273SAli.Bahrami@Sun.COM conv_iter_elfcap(const elfcap_desc_t *cdp, uint_t cnum,
779273SAli.Bahrami@Sun.COM     Conv_fmt_flags_t fmt_flags, conv_iter_cb_t func, void *uvalue)
780Sstevel@tonic-gate {
799273SAli.Bahrami@Sun.COM 	const char	*str;
809273SAli.Bahrami@Sun.COM 
819273SAli.Bahrami@Sun.COM 	fmt_flags = CONV_TYPE_FMT_ALT(fmt_flags);
820Sstevel@tonic-gate 
839273SAli.Bahrami@Sun.COM 	for (; cnum-- > 0; cdp++) {
849273SAli.Bahrami@Sun.COM 		/*
859273SAli.Bahrami@Sun.COM 		 * Skip "reserved" bits. These are unassigned bits in the
869273SAli.Bahrami@Sun.COM 		 * middle of the assigned range.
879273SAli.Bahrami@Sun.COM 		 */
889273SAli.Bahrami@Sun.COM 		if (cdp->c_val == 0)
899273SAli.Bahrami@Sun.COM 			continue;
900Sstevel@tonic-gate 
919273SAli.Bahrami@Sun.COM 		switch (fmt_flags) {
929273SAli.Bahrami@Sun.COM 		default:
939273SAli.Bahrami@Sun.COM 			str = cdp->c_full.s_str;
949273SAli.Bahrami@Sun.COM 			break;
959273SAli.Bahrami@Sun.COM 		case CONV_FMT_ALT_CFNP:
969273SAli.Bahrami@Sun.COM 			str = cdp->c_uc.s_str;
979273SAli.Bahrami@Sun.COM 			break;
989273SAli.Bahrami@Sun.COM 		case CONV_FMT_ALT_NF:
999273SAli.Bahrami@Sun.COM 			str = cdp->c_lc.s_str;
1009273SAli.Bahrami@Sun.COM 			break;
1019273SAli.Bahrami@Sun.COM 		}
1020Sstevel@tonic-gate 
1039273SAli.Bahrami@Sun.COM 		if ((* func)(str, cdp->c_val, uvalue) == CONV_ITER_DONE)
1049273SAli.Bahrami@Sun.COM 			return (CONV_ITER_DONE);
1059273SAli.Bahrami@Sun.COM 	}
1069273SAli.Bahrami@Sun.COM 
1079273SAli.Bahrami@Sun.COM 	return (CONV_ITER_CONT);
1080Sstevel@tonic-gate }
1090Sstevel@tonic-gate 
1109273SAli.Bahrami@Sun.COM /*
1119273SAli.Bahrami@Sun.COM  * Iterate the strings for CA_SUNW_HW1
1129273SAli.Bahrami@Sun.COM  */
1139273SAli.Bahrami@Sun.COM conv_iter_ret_t
1149273SAli.Bahrami@Sun.COM conv_iter_cap_val_hw1(Half mach, Conv_fmt_flags_t fmt_flags,
1159273SAli.Bahrami@Sun.COM     conv_iter_cb_t func, void *uvalue)
1160Sstevel@tonic-gate {
1179273SAli.Bahrami@Sun.COM 	if ((mach == EM_386) || (mach == EM_486) ||
1189273SAli.Bahrami@Sun.COM 	    (mach == EM_AMD64) || (mach == CONV_MACH_ALL))
1199273SAli.Bahrami@Sun.COM 		if (conv_iter_elfcap(elfcap_getdesc_hw1_386(),
1209273SAli.Bahrami@Sun.COM 		    ELFCAP_NUM_HW1_386, fmt_flags, func, uvalue) ==
1219273SAli.Bahrami@Sun.COM 		    CONV_ITER_DONE)
1229273SAli.Bahrami@Sun.COM 			return (CONV_ITER_DONE);
1230Sstevel@tonic-gate 
1249273SAli.Bahrami@Sun.COM 	if ((mach == EM_SPARC) || (mach == EM_SPARC32PLUS) ||
1259273SAli.Bahrami@Sun.COM 	    (mach == EM_SPARCV9) || (mach == CONV_MACH_ALL))
1269273SAli.Bahrami@Sun.COM 		if (conv_iter_elfcap(elfcap_getdesc_hw1_sparc(),
1279273SAli.Bahrami@Sun.COM 		    ELFCAP_NUM_HW1_SPARC, fmt_flags, func, uvalue) ==
1289273SAli.Bahrami@Sun.COM 		    CONV_ITER_DONE)
1299273SAli.Bahrami@Sun.COM 			return (CONV_ITER_DONE);
1309273SAli.Bahrami@Sun.COM 
1319273SAli.Bahrami@Sun.COM 	return (CONV_ITER_CONT);
1320Sstevel@tonic-gate }
1330Sstevel@tonic-gate 
1349273SAli.Bahrami@Sun.COM /*
1359273SAli.Bahrami@Sun.COM  * Iterate the strings for CA_SUNW_SF1
1369273SAli.Bahrami@Sun.COM  */
1379273SAli.Bahrami@Sun.COM conv_iter_ret_t
1389273SAli.Bahrami@Sun.COM conv_iter_cap_val_sf1(Conv_fmt_flags_t fmt_flags, conv_iter_cb_t func,
1399273SAli.Bahrami@Sun.COM     void *uvalue)
1400Sstevel@tonic-gate {
1419273SAli.Bahrami@Sun.COM 	return (conv_iter_elfcap(elfcap_getdesc_sf1(), ELFCAP_NUM_SF1,
1429273SAli.Bahrami@Sun.COM 	    fmt_flags, func, uvalue));
1430Sstevel@tonic-gate }
144