Search
lxdream.org :: lxdream/test/testta.c
lxdream 0.9.1
released Jun 29
Download Now
filename test/testta.c
changeset 754:35c496703380
prev561:533f6b478071
author nkeynes
date Sun Jul 20 11:37:47 2008 +0000 (11 years ago)
permissions -rw-r--r--
last change Commit testta changes for sort-dma tests
file annotate diff log raw
nkeynes@185
     1
/**
nkeynes@561
     2
 * $Id$
nkeynes@185
     3
 * 
nkeynes@185
     4
 * Tile Accelerator test cases 
nkeynes@185
     5
 *
nkeynes@185
     6
 * Copyright (c) 2006 Nathan Keynes.
nkeynes@185
     7
 *
nkeynes@185
     8
 * This program is free software; you can redistribute it and/or modify
nkeynes@185
     9
 * it under the terms of the GNU General Public License as published by
nkeynes@185
    10
 * the Free Software Foundation; either version 2 of the License, or
nkeynes@185
    11
 * (at your option) any later version.
nkeynes@185
    12
 *
nkeynes@185
    13
 * This program is distributed in the hope that it will be useful,
nkeynes@185
    14
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
nkeynes@185
    15
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
nkeynes@185
    16
 * GNU General Public License for more details.
nkeynes@185
    17
 */
nkeynes@185
    18
nkeynes@185
    19
#include <stdio.h>
nkeynes@185
    20
#include "testdata.h"
nkeynes@185
    21
#include "pvr.h"
nkeynes@185
    22
#include "lib.h"
nkeynes@185
    23
#include "asic.h"
nkeynes@185
    24
nkeynes@185
    25
#define DMA_ALIGN(x)   ((void *)((((unsigned int)(x))+0x1F)&0xFFFFFFE0))
nkeynes@185
    26
nkeynes@185
    27
#define OBJ_START 0x00010000
nkeynes@190
    28
#define OBJ_LENGTH 0x00010000
nkeynes@185
    29
#define TILE_START 0x00060000
nkeynes@190
    30
#define TILE_LENGTH 0x00010000
nkeynes@190
    31
nkeynes@190
    32
#define MEM_FILL 0xFE
nkeynes@190
    33
nkeynes@190
    34
int ta_tile_sizes[4] = { 0, 32, 64, 128 };
nkeynes@190
    35
nkeynes@190
    36
#define TILE_SIZE(cfg, tile) ta_tile_sizes[((((cfg->ta_cfg) >> (4*tile))&0x03))]
nkeynes@190
    37
nkeynes@190
    38
struct ta_config default_ta_config = { 0x00111111, GRID_SIZE(640,480), OBJ_START,
nkeynes@190
    39
				       OBJ_START+OBJ_LENGTH, TILE_START+TILE_LENGTH,
nkeynes@190
    40
				       TILE_START, TILE_START+TILE_LENGTH };
nkeynes@190
    41
nkeynes@190
    42
nkeynes@190
    43
int tile_sizes[5];
nkeynes@190
    44
int tile_events[5] = { EVENT_PVR_OPAQUE_DONE, EVENT_PVR_OPAQUEMOD_DONE,
nkeynes@190
    45
		       EVENT_PVR_TRANS_DONE, EVENT_PVR_TRANSMOD_DONE,
nkeynes@190
    46
		       EVENT_PVR_PUNCHOUT_DONE };
nkeynes@190
    47
char *tile_names[5] = { "Opaque", "Opaque Mod", "Trans", "Trans Mod", "Punch Out" };
nkeynes@185
    48
nkeynes@185
    49
#define FLOAT(p) *((float *)(p))
nkeynes@185
    50
nkeynes@190
    51
void make_expected_buffer( test_data_block_t expected_block, char *expect, int length )
nkeynes@190
    52
{
nkeynes@190
    53
    memset( expect, MEM_FILL,length );
nkeynes@190
    54
    
nkeynes@190
    55
    if( expected_block != NULL ) {
nkeynes@190
    56
	if( expected_block->length > length ) {
nkeynes@190
    57
	    fprintf( stderr, "Test data error: expected tile length is %d, but tile size is only %d\n", expected_block->length, length );
nkeynes@190
    58
	    return;
nkeynes@190
    59
	}
nkeynes@190
    60
	memcpy( expect, expected_block->data, expected_block->length );
nkeynes@190
    61
	
nkeynes@190
    62
	if( expected_block->length <= length-4 ) {
nkeynes@190
    63
	    *((unsigned int *)&expect[expected_block->length]) = 0xF0000000;
nkeynes@190
    64
	}
nkeynes@190
    65
    }
nkeynes@190
    66
}
nkeynes@190
    67
nkeynes@190
    68
int tilematrix_block_compare( test_data_block_t expected_block, char *tile_ptrs[], int tile_type, int offset )
nkeynes@190
    69
{
nkeynes@190
    70
    int tile_size = tile_sizes[tile_type];
nkeynes@190
    71
    char expect[tile_size];
nkeynes@190
    72
nkeynes@190
    73
    make_expected_buffer(expected_block, expect, tile_size);
nkeynes@190
    74
    return memcmp( expect, tile_ptrs[tile_type]+(offset*tile_sizes[tile_type]), tile_size );
nkeynes@190
    75
}
nkeynes@190
    76
nkeynes@212
    77
/**
nkeynes@212
    78
 * Copy from vram, wrapping appropriately 
nkeynes@212
    79
 */
nkeynes@212
    80
int memcpy_from_vram( char *dest, char *src, int len ) 
nkeynes@212
    81
{
nkeynes@212
    82
    while( len > 0 ) {
nkeynes@212
    83
	*dest++ = *src++;
nkeynes@212
    84
	src = (char *)( ((unsigned int)src) & 0xFF7FFFFF );
nkeynes@212
    85
	len--;
nkeynes@212
    86
    }
nkeynes@212
    87
}
nkeynes@212
    88
nkeynes@185
    89
int test_ta( test_data_t test_case )
nkeynes@185
    90
{
nkeynes@185
    91
    char buf[1024];
nkeynes@185
    92
    unsigned int *p = DMA_ALIGN(buf);
nkeynes@185
    93
    unsigned int *data = p;
nkeynes@190
    94
    int haveFailure = 0;
nkeynes@190
    95
    int checkedTile[5] = {0,0,0,0,0};
nkeynes@190
    96
    int i;
nkeynes@190
    97
    int hsegs,vsegs;
nkeynes@190
    98
    char *tile_ptrs[5];
nkeynes@185
    99
nkeynes@185
   100
    asic_clear();
nkeynes@185
   101
nkeynes@190
   102
    memset( PVR_VRAM_BASE, MEM_FILL,  0x00090000 );
nkeynes@190
   103
    test_data_block_t config_data = get_test_data( test_case, "config" );
nkeynes@190
   104
    struct ta_config *config = &default_ta_config;
nkeynes@190
   105
    if( config_data != NULL ) {
nkeynes@190
   106
	if( config_data->length != sizeof(struct ta_config) ) {
nkeynes@190
   107
	    fprintf( stderr, "Invalid config data length %d - aborting test %s\n",
nkeynes@190
   108
		     config_data->length, test_case->test_name );
nkeynes@190
   109
	    return -1;
nkeynes@190
   110
	}
nkeynes@190
   111
	config = (struct ta_config *)config_data->data;
nkeynes@190
   112
    }
nkeynes@212
   113
    char *result = (char *)(PVR_VRAM_BASE+config->obj_start);
nkeynes@212
   114
    char *tilematrix = (char *)(PVR_VRAM_BASE+config->tile_start);
nkeynes@212
   115
nkeynes@190
   116
    ta_init(config);
nkeynes@190
   117
    for( i=0; i<5; i++ ) {
nkeynes@190
   118
	tile_sizes[i] = TILE_SIZE(config,i);
nkeynes@190
   119
    }
nkeynes@190
   120
    hsegs = (config->grid_size & 0xFFFF)+1;
nkeynes@190
   121
    vsegs = (config->grid_size >> 16) + 1;
nkeynes@190
   122
    tile_ptrs[0] = tilematrix;
nkeynes@190
   123
    tile_ptrs[1] = tile_ptrs[0] + (hsegs*vsegs*tile_sizes[0]);
nkeynes@190
   124
    tile_ptrs[2] = tile_ptrs[1] + (hsegs*vsegs*tile_sizes[1]);
nkeynes@190
   125
    tile_ptrs[3] = tile_ptrs[2] + (hsegs*vsegs*tile_sizes[2]);
nkeynes@190
   126
    tile_ptrs[4] = tile_ptrs[3] + (hsegs*vsegs*tile_sizes[3]);
nkeynes@190
   127
nkeynes@185
   128
nkeynes@185
   129
    test_data_block_t input = get_test_data(test_case, "input");
nkeynes@212
   130
    test_data_block_t input2 = get_test_data(test_case, "input2");
nkeynes@185
   131
    test_data_block_t output = get_test_data(test_case, "output");
nkeynes@190
   132
    test_data_block_t error = get_test_data(test_case, "error");
nkeynes@754
   133
    test_data_block_t sortconf = get_test_data(test_case, "sortconf");
nkeynes@754
   134
    test_data_block_t sorttab = get_test_data(test_case, "sorttab");
nkeynes@754
   135
    
nkeynes@185
   136
    if( input == NULL || output == NULL ) {
nkeynes@185
   137
	fprintf( stderr, "Skipping test case '%s': data incomplete\n", test_case->test_name );
nkeynes@185
   138
	return -1;
nkeynes@185
   139
    }
nkeynes@185
   140
nkeynes@754
   141
    if( sortconf != NULL && sorttab != NULL ) {
nkeynes@754
   142
        if( sortconf->length != 8 ) {
nkeynes@754
   143
            fprintf( stderr, "Invalid sort config length: %d - abort test %s\n", 
nkeynes@754
   144
                     sortconf->length, test_case->test_name );
nkeynes@754
   145
            return -1;
nkeynes@754
   146
        }
nkeynes@754
   147
        uint32_t *sc = (uint32_t *)sortconf->data;
nkeynes@754
   148
        if( sort_dma_write( sorttab->data, sorttab->length, input->data, input->length, *sc, *(sc+1) ) == -1 ){
nkeynes@754
   149
            return -1;
nkeynes@754
   150
        }
nkeynes@754
   151
    } else {
nkeynes@754
   152
        if( pvr_dma_write( 0x10000000, input->data, input->length, 0 ) == -1 ) {
nkeynes@754
   153
            return -1;
nkeynes@754
   154
        }
nkeynes@185
   155
    }
nkeynes@190
   156
nkeynes@212
   157
    if( input2 != NULL ) {
nkeynes@754
   158
        ta_reinit();
nkeynes@754
   159
        pvr_dma_write( 0x10000000, input2->data, input2->length, 0 );
nkeynes@212
   160
    }
nkeynes@212
   161
    
nkeynes@212
   162
nkeynes@190
   163
    if( error != NULL ) {
nkeynes@190
   164
	for( i=0; i<error->length; i++ ) {
nkeynes@190
   165
	    if( asic_wait( error->data[i] ) == -1 ) {
nkeynes@190
   166
		fprintf( stderr, "Test %s: failed (Timeout waiting for error event %d)\n",
nkeynes@190
   167
			 test_case->test_name, error->data[i] );
nkeynes@190
   168
		asic_dump( stderr );
nkeynes@190
   169
		return -1;
nkeynes@190
   170
	    }
nkeynes@190
   171
	}
nkeynes@185
   172
    }
nkeynes@185
   173
nkeynes@190
   174
    for( i=0; i<MAX_DATA_BLOCKS; i++ ) {
nkeynes@190
   175
	test_data_block_t data = &test_case->item[i];
nkeynes@190
   176
	int tile, x, y, offset;
nkeynes@190
   177
	if( data->name != NULL ) {
nkeynes@190
   178
	    int result = sscanf( data->name, "tile %d %dx%d", &tile, &x, &y );
nkeynes@190
   179
	    if( result == 1 ) {
nkeynes@190
   180
		x = y = 0;
nkeynes@190
   181
	    } else if( result != 3 ) {
nkeynes@190
   182
		continue;
nkeynes@190
   183
	    }
nkeynes@190
   184
	    tile--;
nkeynes@190
   185
	    offset = x + (y * hsegs);
nkeynes@190
   186
nkeynes@190
   187
	    if( checkedTile[tile] == 0 ) {
nkeynes@190
   188
		if( asic_wait( tile_events[tile] ) == -1 ) {
nkeynes@190
   189
		    fprintf( stderr, "Test %s: failed (Timeout waiting for %s done event)\n", 
nkeynes@190
   190
			     test_case->test_name, tile_names[tile] );
nkeynes@190
   191
		    ta_dump_regs();
nkeynes@190
   192
		    asic_dump( stderr );
nkeynes@190
   193
		    haveFailure = 1;
nkeynes@190
   194
		}
nkeynes@190
   195
	    }
nkeynes@190
   196
nkeynes@190
   197
	    if( tilematrix_block_compare( data, tile_ptrs, tile, offset ) != 0 ) {
nkeynes@190
   198
		fprintf( stderr, "Test %s: Failed (%s matrix %dx%d). ", 
nkeynes@190
   199
			 test_case->test_name, tile_names[tile], x, y );
nkeynes@190
   200
		fwrite_diff32( stderr, data->data, data->length, 
nkeynes@190
   201
			       tile_ptrs[tile] + (tile_sizes[tile]*offset), tile_sizes[tile] );
nkeynes@190
   202
		haveFailure = 1;
nkeynes@190
   203
	    }
nkeynes@190
   204
	    checkedTile[tile] = 1;
nkeynes@190
   205
	}
nkeynes@190
   206
    }
nkeynes@190
   207
nkeynes@190
   208
    /* Overflow */
nkeynes@190
   209
    test_data_block_t plist = get_test_data(test_case, "plist" );
nkeynes@190
   210
    if( plist != NULL ) {
nkeynes@190
   211
	unsigned int plist_posn, plist_end;
nkeynes@190
   212
	if( config->ta_cfg & 0x00100000 ) { /* Descending */
nkeynes@193
   213
	    plist_posn = pvr_get_plist_posn(); //+ tile_sizes[0];
nkeynes@190
   214
	    plist_end = config->plist_start;
nkeynes@190
   215
	} else {
nkeynes@190
   216
	    plist_posn = config->plist_start;
nkeynes@193
   217
	    plist_end = pvr_get_plist_posn() + tile_sizes[0];
nkeynes@190
   218
	}
nkeynes@190
   219
	char *plist_data = (char *)(PVR_VRAM_BASE + plist_posn);
nkeynes@190
   220
	if( test_block_compare( plist, plist_data, plist_end-plist_posn ) != 0 ) {
nkeynes@190
   221
	    fprintf( stderr, "Test %s: Failed (Plist buffer)", test_case->test_name );
nkeynes@190
   222
	    fwrite_diff32( stderr, plist->data, plist->length, (char *)plist_data, 
nkeynes@190
   223
			   plist_end - plist_posn );
nkeynes@190
   224
	    haveFailure = 1;
nkeynes@190
   225
	}
nkeynes@193
   226
	char block[tile_sizes[0]];
nkeynes@193
   227
	memset( block, MEM_FILL, tile_sizes[0] );
nkeynes@193
   228
	if( memcmp( block, plist_data - tile_sizes[0], tile_sizes[0] ) != 0 ) {
nkeynes@193
   229
	    fprintf( stderr, "Test %s: Failed (Plist buffer)", test_case->test_name );
nkeynes@193
   230
	    fwrite_diff32( stderr, block, tile_sizes[0], plist_data - tile_sizes[0],
nkeynes@193
   231
			   tile_sizes[0]);
nkeynes@193
   232
	    haveFailure = 1;
nkeynes@193
   233
	}
nkeynes@190
   234
    }
nkeynes@190
   235
nkeynes@190
   236
    /* Vertex buffer */
nkeynes@185
   237
    int result_length = pvr_get_objbuf_size();
nkeynes@212
   238
    char tmp[result_length];
nkeynes@212
   239
    memcpy_from_vram( tmp, result, result_length );
nkeynes@212
   240
    if( test_block_compare( output, tmp, result_length ) != 0 ) {
nkeynes@190
   241
	fprintf( stderr, "Test %s: Failed (Vertex buffer). ", test_case->test_name );
nkeynes@212
   242
	fwrite_diff32( stderr, output->data, output->length, tmp, result_length );
nkeynes@190
   243
	haveFailure = 1;
nkeynes@185
   244
    }
nkeynes@185
   245
    
nkeynes@190
   246
nkeynes@190
   247
    for( i=0; i<5; i++ ) {
nkeynes@190
   248
	if( checkedTile[i] == 0 ) {
nkeynes@190
   249
	    if( tilematrix_block_compare( NULL, tile_ptrs, i, 0 ) != 0 ) {
nkeynes@190
   250
		fprintf( stderr, "Test %s: Failed (%s matrix). ", test_case->test_name, tile_names[i] );
nkeynes@190
   251
                fprintf( stderr, "Expected empty buffer at %08X, but was =>\n", 
nkeynes@190
   252
			 (unsigned int)(tile_ptrs[i]) );
nkeynes@190
   253
		fwrite_dump( stderr, tile_ptrs[i], tile_sizes[i] );
nkeynes@190
   254
		//		fwrite_dump( stderr, tile_ptrs[i] - 128, 256 );
nkeynes@190
   255
			 
nkeynes@190
   256
	    }
nkeynes@190
   257
	}
nkeynes@190
   258
    }
nkeynes@193
   259
nkeynes@193
   260
    if( error == NULL ) {
nkeynes@193
   261
	if( asic_check(EVENT_TA_ERROR) || asic_check(EVENT_PVR_PRIM_ALLOC_FAIL) ||
nkeynes@193
   262
	    asic_check(EVENT_PVR_MATRIX_ALLOC_FAIL) || asic_check(EVENT_PVR_BAD_INPUT) ) {
nkeynes@193
   263
	    fprintf( stderr, "Test %s: Failed (unexpected error events)\n", test_case->test_name );
nkeynes@193
   264
	    asic_dump( stderr );
nkeynes@193
   265
	    haveFailure = 1;
nkeynes@193
   266
	}
nkeynes@193
   267
    }
nkeynes@193
   268
nkeynes@190
   269
    if( haveFailure )
nkeynes@190
   270
	return -1;
nkeynes@190
   271
nkeynes@190
   272
    fprintf( stdout, "Test %s: OK\n", test_case->test_name );
nkeynes@190
   273
    return 0;
nkeynes@185
   274
}
nkeynes@185
   275
nkeynes@185
   276
int main( int argc, char *argv[] ) 
nkeynes@185
   277
{
nkeynes@185
   278
    int test_cases = 0;
nkeynes@185
   279
    int test_failures = 0;
nkeynes@185
   280
    test_data_t test_data = load_test_dataset(stdin);
nkeynes@185
   281
    test_data_t test_case = test_data;
nkeynes@185
   282
nkeynes@185
   283
    asic_mask_all();
nkeynes@185
   284
    pvr_init();
nkeynes@185
   285
nkeynes@185
   286
    while( test_case != NULL ) {
nkeynes@185
   287
	test_cases++;
nkeynes@185
   288
	int result = test_ta(test_case);
nkeynes@185
   289
	if( result != 0 ) {
nkeynes@185
   290
	    test_failures++;
nkeynes@185
   291
	}
nkeynes@185
   292
	test_case = test_case->next;
nkeynes@185
   293
    }
nkeynes@185
   294
    free_test_dataset(test_data);
nkeynes@185
   295
    if( test_failures != 0 ) {
nkeynes@185
   296
	fprintf( stderr, "%d/%d test failures!\n", test_failures, test_cases );
nkeynes@185
   297
	return 1;
nkeynes@185
   298
    } else {
nkeynes@185
   299
	fprintf( stderr, "%d tests OK\n", test_cases );
nkeynes@185
   300
	return 0;
nkeynes@185
   301
    }
nkeynes@185
   302
}
.