Closed tdh8316 closed 1 year ago
Hi,
Thanks for your message. The kernel load address should still be 0x80000
.
I suspect you have an issue with your kernel.c.
All the best, Adam
You intrigued me, so I had a play tonight!
I couldn't get your code to work, but I put this together... It does exactly what you expect yours to do and I've tested it (with a LED and a resistor).
It doesn't help me work out what's wrong with your code, but at least it proves it should work (and all this at load address 0x80000
).
All the best and happy bug hunting! Adam
#define PERIPHERAL_BASE 0xFE000000
#define GPFSEL0 PERIPHERAL_BASE + 0x200000
#define GPSET0 PERIPHERAL_BASE + 0x20001C
#define GPCLR0 PERIPHERAL_BASE + 0x200028
#define GPIO_FUNCTION_OUT 1
#define GPIO_MAX_PIN 53
void mmio_write(long reg, unsigned int val) { *(volatile unsigned int *)reg = val; }
unsigned int mmio_read(long reg) { return *(volatile unsigned int *)reg; }
unsigned int gpio_call(unsigned int pin_number, unsigned int value, unsigned int base, unsigned int field_size, unsigned int field_max) {
unsigned int field_mask = (1 << field_size) - 1;
if (pin_number > field_max) return 0;
if (value > field_mask) return 0;
unsigned int num_fields = 32 / field_size;
unsigned int reg = base + ((pin_number / num_fields) * 4);
unsigned int shift = (pin_number % num_fields) * field_size;
unsigned int curval = mmio_read(reg);
curval &= ~(field_mask << shift);
curval |= value << shift;
mmio_write(reg, curval);
return 1;
}
unsigned int gpio_set(unsigned int pin_number, unsigned int value) { return gpio_call(pin_number, value, GPSET0, 1, GPIO_MAX_PIN); }
unsigned int gpio_clear(unsigned int pin_number, unsigned int value) { return gpio_call(pin_number, value, GPCLR0, 1, GPIO_MAX_PIN); }
unsigned int gpio_function(unsigned int pin_number, unsigned int value) { return gpio_call(pin_number, value, GPFSEL0, 3, GPIO_MAX_PIN); }
int main(void)
{
gpio_function(21, GPIO_FUNCTION_OUT);
while (1)
{
gpio_set(21, 1);
gpio_clear(21, 1);
}
}
Hi! first of all, thank you for writing this guide. I followed everything in part 2-building and wrote my own kernel.c due to I have no UART connector.
And I made the latest Raspbian-Lite (64bit) micro SD card using raspberry pi imager. Then replaced the
kernel8.img
.I expected GPIO21 (40 for hardware) to generate spikes, but it didn't. I'm not even sure whether the boot sequence is done; I found this post on the forum. They say the kernel load address is changed to 0x200000.
Is this guide affected by that post? If not, I'll assume that the
kernel.c
contains problems.