diff --git a/thorn/include/kernel/mailbox.h b/thorn/include/kernel/mailbox.h index b4f6dd8..f5659a2 100644 --- a/thorn/include/kernel/mailbox.h +++ b/thorn/include/kernel/mailbox.h @@ -30,11 +30,14 @@ typedef enum { typedef struct { - unsigned int data : 28;// most significant bits contain shared memory address - channel_t channel : 4; // least four significant bits contain channel -} mbox_message_t; + channel_t channel : 4; // least four significant bits (LSB) contain channel + unsigned int data : 28;// most significant bits (MSB) contain 28 MSB of shared memory address so that `mailbox_message_t` is in the proper format the mailbox expects. The 4 LSB are 0 anyways. +} mailbox_message_t; // Send message and check responses -bool mailbox_request (volatile unsigned int * data_ptr, channel_t channel); +bool mailbox_request (volatile unsigned int * buffer, channel_t channel); +unsigned int mailbox_message_to_register_value (mailbox_message_t message); +void mailbox_read (mailbox_message_t message); +void mailbox_write (mailbox_message_t message); #endif//_ROSE_K_MAILBOX_H diff --git a/thorn/include/kernel/peripherals/mailbox.h b/thorn/include/kernel/peripherals/mailbox.h index 37f664c..f805299 100644 --- a/thorn/include/kernel/peripherals/mailbox.h +++ b/thorn/include/kernel/peripherals/mailbox.h @@ -3,17 +3,30 @@ #include "base.h" -#define MBOX0 (PBASE + 0xB880)// Read from CPU -#define MBOX1 (PBASE + 0xB840)// Write to CPU +// Mailbox base register +#define MAILBOX_BASE (PBASE + 0xB880) -#define MBOX_READ 0x00 -#define MBOX_STATUS 0x18 -#define MBOX_IRQ 0x1C -#define MBOX_WRITE 0x20 +// Mailbox 0 registers (read mailbox) +#define MAILBOX_READ (MAILBOX_BASE)// Reading from the VC +#define MAILBOX_READ_PEEK (MAILBOX_BASE + 0x10) +#define MAILBOX_READ_SENDER (MAILBOX_BASE + 0x14) +#define MAILBOX_READ_STATUS (MAILBOX_BASE + 0x18)// Queue status +#define MAILBOX_READ_CONFIG (MAILBOX_BASE + 0x1C)// Interrupt configuration -#define MBOX_READ_EMPTY (1 << 30) -#define MBOX_WRITE_FULL (1 << 31) +// Mailbox 1 registers (write mailbox) +#define MAILBOX_WRITE (MAILBOX_BASE + 0x20)// Writing to the VC +#define MAILBOX_WRITE_PEEK (MAILBOX_BASE + 0x10) +#define MAILBOX_WRITE_SENDER (MAILBOX_BASE + 0x14) +#define MAILBOX_WRITE_STATUS (MAILBOX_BASE + 0x18)// Queue status +#define MAILBOX_WRITE_CONFIG (MAILBOX_BASE + 0x1C)// Interrupt configuration -#define MBOX_SUCCESS 0x80000000 +// Mailbox status fields +#define MAILBOX_STATUS_EMPTY (1 << 30) +#define MAILBOX_STATUS_FULL (1 << 31) -#endif//_ROSE_K_P_MAILBOX_H \ No newline at end of file +// Property channel request response codes +#define PROPERTY_REQUEST 0x00000000 +#define PROPERTY_RESPONSE_SUCCESS 0x80000000 +#define PROPERTY_RESPONSE_ERROR 0x80000001 + +#endif//_ROSE_K_P_MAILBOX_H diff --git a/thorn/src/kernel/boot.S b/thorn/src/kernel/boot.S index abfd307..c0ed697 100644 --- a/thorn/src/kernel/boot.S +++ b/thorn/src/kernel/boot.S @@ -6,19 +6,19 @@ .globl _start _start: - mrs x0, mpidr_el1 - and x0, x0,#0xFF // Check processor id - cbz x0, init_bss // Hang for all non-primary CPU + mrs x0, mpidr_el1 // Move content of program state register into x0 + and x0, x0,#0xFF // Discard most significant 3 bytes + cbz x0, init_bss // Hang for all non-primary CPU - wfe + wfe // Wait for CPU 0 to finish - b master + b master init_bss: adr x0, bss_begin adr x1, bss_end sub x1, x1, x0 - bl memzero + bl memzero // Zero out BSS section adr x0, move_to_el1 mov x1, #0xe0 @@ -35,31 +35,31 @@ init_bss: b move_to_el1 move_to_el1: - ldr x0, =SCTLR_VALUE_MMU_DISABLED - msr sctlr_el1, x0 + ldr x0, =SCTLR_VALUE_MMU_DISABLED + msr sctlr_el1, x0 // Disable MMU - ldr x0, =HCR_VALUE - msr hcr_el2, x0 + ldr x0, =HCR_VALUE + msr hcr_el2, x0 // Configure hypervisor (= EL 2) - ldr x0, =SPSR_VALUE - msr spsr_el2, x0 + ldr x0, =SPSR_VALUE + msr spsr_el2, x0 - adr x0, master - msr elr_el2, x0 + adr x0, master + msr elr_el2, x0 // Move master address into exception link register - eret + eret // Exception return to go from EL 2 to EL 1 master: - mrs x0, mpidr_el1 - and x0, x0, #0xFF - mov x1, #SECTION_SIZE - mul x1, x1, x0 - add x1, x1, #LOW_MEMORY - mov sp, x1 + mrs x0, mpidr_el1 + and x0, x0, #0xFF + mov x1, #SECTION_SIZE + mul x1, x1, x0 + add x1, x1, #LOW_MEMORY + mov sp, x1 - bl kernel_main - b proc_hang // should never come here + bl kernel_main + b proc_hang // should never come here proc_hang: - b proc_hang + b proc_hang diff --git a/thorn/src/kernel/kernel.c b/thorn/src/kernel/kernel.c index 83af876..40603b0 100644 --- a/thorn/src/kernel/kernel.c +++ b/thorn/src/kernel/kernel.c @@ -21,7 +21,7 @@ void user_process1 (char * array) { for (int i = 0; i < 5; i++) { buf[0] = array[i]; call_sys_write (buf); - delay (100000); + delay (200000); } } } @@ -64,11 +64,13 @@ void kernel_process () { void kernel_init (void) { uart_init (); printf_register (putc); + irq_vector_init (); timer_init (); enable_interrupt_controller (); enable_irq (); task_init (); + init_rng (); // Turn status led OFF and power led ON @@ -91,9 +93,6 @@ void kernel_init (void) { } } - printf ("|...|...|...|...|\r\n"); - printf ("|\t|\t|\t|\t|\r\n"); - LOG ("Initialisation done"); ERROR ("I'm important!"); } diff --git a/thorn/src/kernel/mailbox.c b/thorn/src/kernel/mailbox.c index a744c50..2ca869c 100644 --- a/thorn/src/kernel/mailbox.c +++ b/thorn/src/kernel/mailbox.c @@ -1,46 +1,16 @@ #include "kernel/mailbox.h" -bool mailbox_request (volatile unsigned int * data_ptr, channel_t channel) { - volatile unsigned int * buffer = data_ptr; - +bool mailbox_request (volatile unsigned int * buffer, channel_t channel) { if (DUMP_BUFFER) { LOG ("Dumping message buffer before sending:"); int_dump ((unsigned int *) buffer); hex_dump ((byte_t *) buffer); } - // 28-bit address (MSB) and 4-bit value (LSB) - unsigned int outgoing = ((unsigned int) ((long) data_ptr) & ~0xF) | (channel & 0xF); - - // Wait until we can write - while (get32 (MBOX0 + MBOX_STATUS) & MBOX_WRITE_FULL) - ; + mailbox_message_t message = {channel, (unsigned long) buffer >> 4}; - // Write the address of our buffer to the mailbox with the channel appended - put32 (MBOX0 + MBOX_WRITE, outgoing); - - unsigned int incoming; - while (1) { - // Is there a reply? - while (get32 (MBOX0 + MBOX_STATUS) & MBOX_READ_EMPTY) - ; - - incoming = get32 (MBOX0 + MBOX_READ); - - // Is it a reply to our message? - if (outgoing == incoming) { - if (buffer[1] != MBOX_SUCCESS) { - if (DUMP_BUFFER) { - LOG ("Dumping failed message buffer:"); - int_dump ((unsigned int *) buffer); - hex_dump ((byte_t *) buffer); - } - - return false; - } - break; - } - } + mailbox_write (message); + mailbox_read (message); if (DUMP_BUFFER) { LOG ("Dumping successful message buffer:"); @@ -48,5 +18,35 @@ bool mailbox_request (volatile unsigned int * data_ptr, channel_t channel) { hex_dump ((byte_t *) buffer); } - return true; + return buffer[1] == PROPERTY_RESPONSE_SUCCESS; +} + +unsigned int mailbox_message_to_register_value (mailbox_message_t message) { + return *(unsigned int *) &message; +} + +void mailbox_write (mailbox_message_t message) { + unsigned int status; + unsigned int raw_message = mailbox_message_to_register_value (message); + + do { + status = get32 (MAILBOX_WRITE_STATUS); + } while (status & MAILBOX_STATUS_FULL); + + put32 (MAILBOX_WRITE, raw_message); +} + +void mailbox_read (mailbox_message_t message) { + unsigned int status; + unsigned int raw_message = mailbox_message_to_register_value (message); + + while (1) { + do { + status = get32 (MAILBOX_READ_STATUS); + } while (status & MAILBOX_STATUS_EMPTY); + + if (get32 (MAILBOX_READ) == raw_message) { + break; + } + } } diff --git a/thorn/src/kernel/mm.c b/thorn/src/kernel/mm.c index 2846f8d..2f2e7ae 100644 --- a/thorn/src/kernel/mm.c +++ b/thorn/src/kernel/mm.c @@ -8,7 +8,7 @@ ptr_t get_free_page () { for (int i = 0; i < PAGING_PAGES; i++) { if (mem_map[i] == 0) { mem_map[i] = 1; - return LOW_MEMORY + i * PAGE_SIZE; + return LOW_MEMORY + 3 * SECTION_SIZE + i * PAGE_SIZE; } } return 0;