/*
 *  Hello World for the CodeWarrior
 *  © 1997 Metrowerks Corp.
 *
 *  Questions and comments to:
 *       <mailto:support@metrowerks.com>
 *       <http://www.metrowerks.com/>
 */

#include <stdio.h>
#include <stdlib.h>
/* #include <stdint.h> */
#include <time.h>

#include <OSUtils.h>

typedef  int int32_t;
typedef unsigned  int uint32_t;

struct nubusfpga_leds_softc {
	uint32_t slotid;
};
struct nubusfpga_leds_softc sc;

uint32_t csr_read_simple(uint32_t offset);
void csr_write_simple(uint32_t value, uint32_t offset);
uint32_t rev(uint32_t d);

uint32_t csr_read_simple(uint32_t offset) {
	uint32_t *addr;
	addr = (uint32_t*)(((0x000000F0 | sc.slotid) << 24) + offset);
	return *addr;
}
void csr_write_simple(uint32_t value, uint32_t offset) {
	uint32_t *addr;
	addr = (uint32_t*)(((0x000000F0 | sc.slotid) << 24) + offset);
	*addr = value;
}

uint32_t rev(uint32_t d) {
	uint32_t r;
	r = 0;

	r |= (d & 0x80808080) >> 7;
	r |= (d & 0x40404040) >> 5;
	r |= (d & 0x20202020) >> 3;
	r |= (d & 0x10101010) >> 1;
	r |= (d & 0x08080808) << 1;
	r |= (d & 0x04040404) << 3;
	r |= (d & 0x02020202) << 5;
	r |= (d & 0x01010101) << 7;

	return r;
}

#define inline
#include "nubusfpga_csr_leds.h"
#undef inline

int main(void)
{
	uint32_t x1 = 0xDEADBEEF, x2 = 0xDEADBEEF;

	sc.slotid = 0x9;

	printf("Test Application for NuBusFPGA\n\n");

	printf("Machine settings: char %d short %d int %d long %d long long %d\n", sizeof(char), sizeof(short int), sizeof(int), sizeof(long int), sizeof(long long int));
	printf("Global access struct is located in 0x%08X\n", &sc);

	printf("Slot id hardwired to 0x%x, check the ID on the card and the ID allocation for the host.\n", sc.slotid);	
	printf("MMU Mode is: %s\n", (int)GetMMUMode() ? "32-bits" : "24-bits");

	printf("Checking HW access by reading Ethernet ROM...\n");

	x1 = *(uint32_t*)0x50F08000;
	x2 = *(uint32_t*)0x50F08004;

	printf("I got 0x%08x 0x%08x (rev: 0x%08x 0x%08x)\n", x1, x2, rev(x1), rev(x2));

	printf("Checking if we see our PROM...\n");

	x1 = (0xF0000000 | (sc.slot_id<<24) | 0x00FFFFFC);
	x2 = *(uint32_t*)x1;

	printf("I got 0x%08x for 0x%08x (rev: 0x%08x for 0x%08x)\n", x2, x1, rev(x2), rev(x1));

	return 0;
}

