Home | History | Annotate | Download | only in fptest
      1 /*
      2  * CDDL HEADER START
      3  *
      4  * The contents of this file are subject to the terms of the
      5  * Common Development and Distribution License (the "License").
      6  * You may not use this file except in compliance with the License.
      7  *
      8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
      9  * or http://www.opensolaris.org/os/licensing.
     10  * See the License for the specific language governing permissions
     11  * and limitations under the License.
     12  *
     13  * When distributing Covered Code, include this CDDL HEADER in each
     14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
     15  * If applicable, add the following below this CDDL HEADER, with the
     16  * fields enclosed by brackets "[]" replaced with your own identifying
     17  * information: Portions Copyright [yyyy] [name of copyright owner]
     18  *
     19  * CDDL HEADER END
     20  */
     21 
     22 /*
     23  * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
     24  * Use is subject to license terms.
     25  */
     26 
     27 #pragma ident	"%Z%%M%	%I%	%E% SMI"
     28 
     29 #include <stdio.h>
     30 #include <stdlib.h>
     31 #include <fp.h>
     32 #include <fps_ereport.h>
     33 
     34 #pragma align 64(datain1, datain2, dataout)
     35 
     36 int cbbcopy(struct fps_test_ereport *report);
     37 static void	asi_bcopy_f0(uint32_t *out, uint32_t *in);
     38 static void	asi_bcopy_f16(uint32_t *out, uint32_t *in);
     39 static void	ax_bcopy(uint32_t *out, uint32_t *in);
     40 
     41 static uint32_t dataout[64];
     42 
     43 static uint32_t datain1[64] = {
     44 0x55555500, 0x55555501, 0xaaaaaa02, 0xaaaaaa03,
     45 0x55555504, 0x55555505, 0xaaaaaa06, 0xaaaaaa07,
     46 0x55555508, 0x55555509, 0xaaaaaa0a, 0xaaaaaa0b,
     47 0x5555550c, 0x5555550d, 0xaaaaaa0e, 0xaaaaaa0f,
     48 0x55555510, 0x55555511, 0xaaaaaa12, 0xaaaaaa13,
     49 0x55555514, 0x55555515, 0xaaaaaa16, 0xaaaaaa17,
     50 0x55555518, 0x55555519, 0xaaaaaa1a, 0xaaaaaa1b,
     51 0x5555551c, 0x5555551d, 0xaaaaaa1e, 0xaaaaaa1f,
     52 0x55555520, 0x55555521, 0xaaaaaa22, 0xaaaaaa23,
     53 0x55555524, 0x55555525, 0xaaaaaa26, 0xaaaaaa27,
     54 0x55555528, 0x55555529, 0xaaaaaa2a, 0xaaaaaa2b,
     55 0x5555552c, 0x5555552d, 0xaaaaaa2e, 0xaaaaaa2f,
     56 0x55555530, 0x55555531, 0xaaaaaa32, 0xaaaaaa33,
     57 0x55555534, 0x55555535, 0xaaaaaa36, 0xaaaaaa37,
     58 0x55555538, 0x55555539, 0xaaaaaa3a, 0xaaaaaa3b,
     59 0x5555553c, 0x5555553d, 0xaaaaaa3e, 0xaaaaaa3f
     60 };
     61 
     62 static uint32_t datain2[64] = {
     63 0xaaaaaaff, 0xaaaaaafe, 0x555555fd, 0x555555fc,
     64 0xaaaaaafb, 0xaaaaaafa, 0x555555f9, 0x555555f8,
     65 0xaaaaaaf7, 0xaaaaaaf6, 0x555555f5, 0x555555f4,
     66 0xaaaaaaf3, 0xaaaaaaf2, 0x555555f1, 0x555555f0,
     67 0xaaaaaaef, 0xaaaaaaee, 0x555555ed, 0x555555ec,
     68 0xaaaaaaeb, 0xaaaaaaea, 0x555555e9, 0x555555e8,
     69 0xaaaaaae7, 0xaaaaaae6, 0x555555e5, 0x555555e4,
     70 0xaaaaaae3, 0xaaaaaae2, 0x555555e1, 0x555555e0,
     71 0xaaaaaadf, 0xaaaaaade, 0x555555dd, 0x555555dc,
     72 0xaaaaaadb, 0xaaaaaada, 0x555555d9, 0x555555d8,
     73 0xaaaaaad7, 0xaaaaaad6, 0x555555d5, 0x555555d4,
     74 0xaaaaaad3, 0xaaaaaad2, 0x555555d1, 0x555555d0,
     75 0xaaaaaacf, 0xaaaaaace, 0x555555cd, 0x555555cc,
     76 0xaaaaaacb, 0xaaaaaaca, 0x555555c9, 0x555555c8,
     77 0xaaaaaac7, 0xaaaaaac6, 0x555555c5, 0x555555c4,
     78 0xaaaaaac3, 0xaaaaaac2, 0x555555c1, 0x555555c0
     79 };
     80 
     81 /*
     82  * cbbcopy(int unit, struct fps_test_ereport *report)
     83  * exercises block load and store path thru floating point
     84  * registers. Returns whether load/store was successful.
     85  * If an error, all relevant data is stored in report.
     86  * Purpose: FRF integraty check thru both block ld/st and P$
     87  * ax/ms pipe for health check online check utility. The utility is intented
     88  * to detect simple stuck at fault not timing related faults.
     89  */
     90 int
     91 cbbcopy(struct fps_test_ereport *report)
     92 {
     93 	int i;
     94 	uint64_t expect;
     95 	uint64_t observe;
     96 
     97 	ax_bcopy(dataout, datain1);
     98 	asi_bcopy_f0(dataout, dataout);
     99 
    100 	for (i = 0; i < 64; i++) {
    101 		if (dataout[i] != datain1[i]) {
    102 			expect = (uint64_t)datain1[i];
    103 			observe = (uint64_t)dataout[i];
    104 			setup_fps_test_struct(NO_EREPORT_INFO, report,
    105 			    6337, &observe, &expect, 1, 1);
    106 
    107 			return (FPU_FOROFFLINE);
    108 		}
    109 	}
    110 
    111 	ax_bcopy(dataout, datain2);
    112 	asi_bcopy_f16(dataout, dataout);
    113 
    114 	for (i = 0; i < 64; i++) {
    115 		if (dataout[i] != datain2[i]) {
    116 			expect = (uint64_t)datain2[i];
    117 			observe = (uint64_t)dataout[i];
    118 			setup_fps_test_struct(NO_EREPORT_INFO, report,
    119 			    6338, &observe, &expect, 1, 1);
    120 
    121 			return (FPU_FOROFFLINE);
    122 		}
    123 	}
    124 
    125 	return (FPU_OK);
    126 }
    127 
    128 /*
    129  * asi_bcopy_f0(uint32_t *out, uint32_t *in)
    130  * does the assembly load/store of in to out
    131  */
    132 /* ARGSUSED */
    133 static void
    134 asi_bcopy_f0(uint32_t *out, uint32_t *in)
    135 {
    136 	asm("ldda	[%i1]0xf8,%f0");
    137 	asm("membar	#Sync");
    138 	asm("stda	%f0,[%i0]0xf0");
    139 	asm("membar	#Sync");
    140 }
    141 
    142 /*
    143  * asi_bcopy_f16(uint32_t *out, uint32_t *in)
    144  * does the assembly load/store of in to out
    145  */
    146 /* ARGSUSED */
    147 static void
    148 asi_bcopy_f16(uint32_t *out, uint32_t *in)
    149 {
    150 	asm("ldda	[%i1]0xf0,%f16");
    151 	asm("membar	#Sync");
    152 	asm("stda	%f16,[%i0]0xf8");
    153 	asm("membar	#Sync");
    154 }
    155 
    156 /*
    157  * ax_bcopy(uint32_t *out, uint32_t *in)
    158  * does the assembly load/store of in to out
    159  */
    160 /* ARGSUSED */
    161 static void
    162 ax_bcopy(uint32_t *out, uint32_t *in)
    163 {
    164 	asm("prefetch	[%i1],21");
    165 	asm("prefetch	[%i1+0x40],21");
    166 	asm("ldd	[%i1],%f16");
    167 	asm("ldd	[%i1+8],%f18");
    168 	asm("ldd	[%i1+0x10],%f20");
    169 	asm("ldd	[%i1+0x18],%f22");
    170 	asm("ldd	[%i1+0x20],%f24");
    171 	asm("ldd	[%i1+0x28],%f26");
    172 	asm("ldd	[%i1+0x30],%f28");
    173 	asm("ldd	[%i1+0x38],%f30");
    174 	asm("ldd	[%i1+0x40],%f32");
    175 
    176 	asm("prefetch	[%i1+0x80],21");
    177 	asm("ldd	[%i1+0x48],%f34");
    178 	asm("ldd	[%i1+0x50],%f36");
    179 	asm("ldd	[%i1+0x58],%f38");
    180 	asm("ldd	[%i1+0x60],%f40");
    181 	asm("ldd	[%i1+0x68],%f42");
    182 	asm("ldd	[%i1+0x70],%f44");
    183 	asm("ldd	[%i1+0x78],%f46");
    184 
    185 	asm("prefetch	[%i1+0xc0],21");
    186 	asm("ldd	[%i1+0x80],%f0");
    187 	asm("ldd	[%i1+0x88],%f2");
    188 	asm("ldd	[%i1+0x90],%f4");
    189 	asm("ldd	[%i1+0x98],%f6");
    190 	asm("ldd	[%i1+0xa0],%f8");
    191 	asm("ldd	[%i1+0xa8],%f10");
    192 	asm("ldd	[%i1+0xb0],%f12");
    193 	asm("ldd	[%i1+0xb8],%f14");
    194 
    195 	asm("ldd	[%i1+0xc0],%f48");
    196 	asm("ldd	[%i1+0xc8],%f50");
    197 	asm("ldd	[%i1+0xd0],%f52");
    198 	asm("ldd	[%i1+0xd8],%f54");
    199 	asm("ldd	[%i1+0xe0],%f56");
    200 	asm("ldd	[%i1+0xe8],%f58");
    201 	asm("ldd	[%i1+0xf0],%f60");
    202 	asm("ldd	[%i1+0xf8],%f62");
    203 
    204 	asm("membar	#Sync");
    205 	asm("stda	%f16,[%i0]0xf8");
    206 	asm("add	%i0,0x40,%i0");
    207 	asm("stda	%f32,[%i0]0xf0");
    208 	asm("add	%i0,0x40,%i0");
    209 	asm("stda	%f0,[%i0]0xf0");
    210 	asm("add	%i0,0x40,%i0");
    211 	asm("stda	%f48,[%i0]0xf0");
    212 	asm("membar	#Sync");
    213 }
    214