#ifndef CACHERACER_H #define CACHERACER_H void __start(int core_id); /** Memory Layout * * Memory layout differs from CS 3410. Here, we have 64MB of memory, * addressable in the range 0x00000000 to 0x04000000. Each player sees * their half of memory as starting at 0x00000000. Player 2 is mapped * in reverse, i.e. their 0x00000000 is Player 1's 0x03FFFFFC. Memory * is byte-addressed. * * The linker script places code beginning at 0x400. Up to 0x00100000 * is read-only memory containing game data. Beginning at 0x00100000 * are the stacks, spaced 1 MB apart. Thus the layout is * * 0x00000000 - 0x00100000: Read-only memory * 0x00100000 - 0x02000000: Your half of read-write memory * TODO: are the below addresses correct? * 0x02000000 - 0x03EFFFFC: Opponent's half of read-write memory * 0x03EFFFFC - 0x04000000: Opponent's read-only memory */ #define PLAYER_RO_SEGMENT_SIZE 0x00100000 #define PLAYER_STACK_SIZE 0x00100000 #define HOME_START 0x00000000 #define HOME_RW_START PLAYER_RO_SEGMENT_SIZE #define HOME_DATA_START (PLAYER_RO_SEGMENT_SIZE + 4 * PLAYER_STACK_SIZE) #define HOME_RW ((void *) HOME_RW_START) #define HOME_DATA ((void *) HOME_DATA_START) /** Definitions of global data */ #define TAUNT_SIZE 228 struct player_status { signed char taunt[TAUNT_SIZE]; }; /** Pointers to global structures */ #define HOME_STATUS ((struct player_status*) (HOME_RW_START - sizeof(struct player_status))) __attribute__ ((unused, noinline)) static void prints(char *fmt) { __asm__ __volatile__ ( "ADDI a1, %0, 0\n\t" "ADDI a0, zero, 22\n\t" "SCALL\n\t" : : "r" (fmt) ); } __attribute__ ((unused, noinline)) static void printi(int i) { /* invoke system call number 22 */ __asm__ __volatile__ ( "ADDI a1, a0, 0\n\t" "ADDI a0, zero, 23\n\t" "SCALL\n\t" ); } __attribute__ ((unused, noinline)) static void sneak_attack() { __asm__ __volatile__ ( "ADDI a0, zero, 24\n\t" "SCALL" ); } #endif