static void spu_memload_stereo8(int leftpos,int rightpos,void *src0,size_t size)
{
	uint8 *src = src0;
	uint32 *left  = (uint32*)(leftpos +SPU_RAM_BASE);
	uint32 *right = (uint32*)(rightpos+SPU_RAM_BASE);
	size = (size+7)/8;
	while(size--) {
		unsigned lval,rval,old;
		lval = *src++;
		rval = *src++;
		lval|= (*src++)<<8;
		rval|= (*src++)<<8;
		lval|= (*src++)<<16;
		rval|= (*src++)<<16;
		lval|= (*src++)<<24;
		rval|= (*src++)<<24;
		g2_fifo_wait();
		G2_LOCK(old);
		*left++=lval;
		*right++=rval;
		G2_UNLOCK(old);
	//	g2_write_32(*left++,lval);
	//	g2_write_32(*right++,rval);
	//	g2_fifo_wait();
	}
}
示例#2
0
文件: testaica.c 项目: hean01/lxdream
int main( int argc, char *argv[] )
{
    char buf[65536] __attribute__((aligned(32)));
    uint32_t aica_addr = AICA_RAM_BASE;
    int len;
    int totallen = 0;

    aica_disable();
    /* Load ARM program from stdin and copy to ARM memory */
    while( (len = read(0, buf, sizeof(buf))) > 0 ) {
        if(memcpy_to_aica( aica_addr, buf, len ) != 0 ) {
            printf( "Failed to load program!\n" );
            return 1;
        }
        aica_addr += len;
        totallen += len;
    }
    printf( "Program loaded (%d bytes)\n", totallen);

    /* Main loop waiting for IO commands */
    aica_enable();
    do {
        g2_fifo_wait();
        irq_disable();
        int syscall = long_read(AICA_SYSCALL);
        irq_enable();
        if( syscall != -1 ) {
            if( syscall == -2 ) {
                fprintf( stderr, "ARM aborted with general exception\n" );
                return -2;
            } else if( syscall == SYS_EXIT ) {
                printf( "Exiting at ARM request\n" );
                aica_disable();
                return long_read(AICA_SYSCALL_ARG1);
            } else {
                uint32_t result = do_syscall( syscall, long_read(AICA_SYSCALL_ARG1),
                                              long_read(AICA_SYSCALL_ARG2), long_read(AICA_SYSCALL_ARG3) );
                g2_fifo_wait();
                irq_disable();
                long_write( AICA_SYSCALL_RETURN, result );
                long_write( AICA_SYSCALL, -1 );
                irq_enable();
            }
        }
    } while( 1 );
}
示例#3
0
/* Transfer one packet of data from the AICA->SH4 queue. Expects to
   find AICA_CMD_MAX_SIZE dwords of space available. Returns -1
   if failure, 0 for no packets available, 1 otherwise. Failure
   might mean a permanent failure since the queue is probably out of sync. */
int snd_aica_to_sh4(void *packetout) {
	uint32	bot, start, stop, top, size, cnt, *pkt32;

	sem_wait(sem_qram);

	/* Set these up for reference */
	bot = SPU_RAM_BASE + AICA_MEM_RESP_QUEUE;
	assert_msg( g2_read_32(bot + offsetof(aica_queue_t, valid)), "Queue is not yet valid" );

	top = SPU_RAM_BASE + AICA_MEM_RESP_QUEUE + g2_read_32(bot + offsetof(aica_queue_t, size));
	start = SPU_RAM_BASE + AICA_MEM_RESP_QUEUE + g2_read_32(bot + offsetof(aica_queue_t, tail));
	stop = SPU_RAM_BASE + AICA_MEM_RESP_QUEUE + g2_read_32(bot + offsetof(aica_queue_t, head));
	cnt = 0;
	pkt32 = (uint32 *)packetout;

	/* Is there anything? */
	if (start == stop) {
		sem_signal(sem_qram);
		return 0;
	}

	/* Check for packet size overflow */
	size = g2_read_32(start + offsetof(aica_cmd_t, size));
	if (cnt >= AICA_CMD_MAX_SIZE) {
		sem_signal(sem_qram);
		dbglog(DBG_ERROR, "snd_aica_to_sh4(): packet larger than %d dwords\n", AICA_CMD_MAX_SIZE);
		return -1;
	}

	/* Find stop point for this packet */
	stop = start + size*4;
	if (stop > top)
		stop -= top - (SPU_RAM_BASE + AICA_MEM_RESP_QUEUE);
	
	while (start != stop) {
		/* Fifo wait if necessary */
		if (!(cnt % 8))
			g2_fifo_wait();
		cnt++;

		/* Read the next dword */
		*pkt32++ = g2_read_32(start);

		/* Move our counters */
		start += 4;
		if (start >= top)
			start = bot;
		cnt++;
	}

	/* Finally, write a new tail value to signify that we've removed a packet */
	g2_write_32(bot + offsetof(aica_queue_t, tail), start - (SPU_RAM_BASE + AICA_MEM_RESP_QUEUE));

	sem_signal(sem_qram);

	return 1;
}
示例#4
0
static void spu_memload_stereo16(int leftpos,int rightpos,void *src0,size_t size)
{
	uint16 *src = src0;
	uint32 *left  = (uint32*)(leftpos +SPU_RAM_BASE);
	uint32 *right = (uint32*)(rightpos+SPU_RAM_BASE);
	size = (size+7)/8;
	while(size--) {
		unsigned lval,rval;
		lval = *src++;
		rval = *src++;
		lval|= (*src++)<<16;
		rval|= (*src++)<<16;
		g2_write_32(left++,lval);
		g2_write_32(right++,rval);
		g2_fifo_wait();
	}
}
示例#5
0
/* Submit a request to the SH4->AICA queue; size is in uint32's */
int snd_sh4_to_aica(void *packet, uint32 size) {
	uint32	qa, bot, start, top, *pkt32, cnt;
	assert_msg( size < 256, "SH4->AICA packets may not be >256 uint32's long" );

	sem_wait(sem_qram);

	/* Set these up for reference */
	qa = SPU_RAM_BASE + AICA_MEM_CMD_QUEUE;
	assert_msg( g2_read_32(qa + offsetof(aica_queue_t, valid)), "Queue is not yet valid" );

	bot = SPU_RAM_BASE + g2_read_32(qa + offsetof(aica_queue_t, data));
	top = bot + g2_read_32(qa + offsetof(aica_queue_t, size));
	start = bot + g2_read_32(qa + offsetof(aica_queue_t, head));
	pkt32 = (uint32 *)packet;
	cnt = 0;

	while (size > 0) {
		/* Fifo wait if necessary */
		if (!(cnt % 8))
			g2_fifo_wait();
		cnt++;

		/* Write the next dword */
		g2_write_32(start, *pkt32++);

		/* Move our counters */
		start += 4;
		if (start >= top)
			start = bot;
		size--;
	}

	/* Finally, write a new head value to signify that we've added
	   a packet for it to process */
	g2_write_32(qa + offsetof(aica_queue_t, head), start - bot);

	/* We could wait until head == tail here for processing, but there's
	   not really much point; it'll just slow things down. */

	sem_signal(sem_qram);

	return 0;
}
示例#6
0
static void spu_memload_stereo16(int leftpos, int rightpos, void *src0, size_t size)
{
	register uint16 *src = src0;

#if 0
	sep_data(src, size, 1);
	dcache_flush_range((unsigned)sep_buffer, size);
	
	dmadest = rightpos;
	dmacnt = size / 2;
	
	spu_dma_transfer(sep_buffer[0], leftpos, size / 2, -1, spu_dma_transfer2, 0);
	//spu_dma_transfer(sep_buffer[1], rightpos, size / 2, -1, NULL, 0);
#else

	register uint32 *left  = (uint32*)(leftpos  + SPU_RAM_BASE);
	register uint32 *right = (uint32*)(rightpos + SPU_RAM_BASE);
	
	size = (size+7)/8;
	unsigned lval, rval, old = 0;
	
	while(size--) {
		
		lval = *src++;
		rval = *src++;
		lval|= (*src++)<<16;
		rval|= (*src++)<<16;
		
		g2_fifo_wait();
		G2_LOCK(old);
		*left++=lval;
		*right++=rval;
		G2_UNLOCK(old);
		/*
		g2_write_32(*left++,lval);
		g2_write_32(*right++,rval);
		g2_fifo_wait();*/
	}
#endif
}