96 lines
2.8 KiB
C
96 lines
2.8 KiB
C
#include <mruby.h>
|
|
|
|
static mrb_value mrb_read32(mrb_state *mrb, mrb_value self) {
|
|
mrb_value addr = mrb_get_arg1(mrb);
|
|
uint32_t addr_int = mrb_integer(addr);
|
|
|
|
if (addr_int % 4 != 0) {
|
|
mrb_raise(mrb, E_ARGUMENT_ERROR, "Address must be 32bits aligned");
|
|
}
|
|
|
|
uint32_t val = *(volatile uint32_t *)(addr_int);
|
|
|
|
return mrb_int_value(mrb, val);
|
|
}
|
|
|
|
static mrb_value mrb_read16(mrb_state *mrb, mrb_value self) {
|
|
mrb_value addr = mrb_get_arg1(mrb);
|
|
uint32_t addr_int = mrb_integer(addr);
|
|
|
|
if (addr_int % 2 != 0) {
|
|
mrb_raise(mrb, E_ARGUMENT_ERROR, "Address must be 16bits aligned");
|
|
}
|
|
|
|
uint16_t val = *(volatile uint16_t *)(addr_int);
|
|
|
|
return mrb_int_value(mrb, val);
|
|
}
|
|
|
|
static mrb_value mrb_read8(mrb_state *mrb, mrb_value self) {
|
|
mrb_value addr = mrb_get_arg1(mrb);
|
|
uint32_t addr_int = mrb_integer(addr);
|
|
|
|
uint8_t val = *(volatile uint8_t *)(addr_int);
|
|
|
|
return mrb_int_value(mrb, val);
|
|
}
|
|
|
|
static mrb_value mrb_write32(mrb_state *mrb, mrb_value self) {
|
|
mrb_value addr, value;
|
|
mrb_get_args(mrb, "i|i", &addr, &value);
|
|
|
|
uint32_t addr_int = mrb_integer(addr);
|
|
uint32_t value_int = mrb_integer(value);
|
|
|
|
if (addr_int % 4 != 0) {
|
|
mrb_raise(mrb, E_ARGUMENT_ERROR, "Address must be 32bits aligned");
|
|
}
|
|
|
|
*(volatile uint16_t *)(addr_int) = value_int;
|
|
|
|
return self;
|
|
}
|
|
|
|
static mrb_value mrb_write16(mrb_state *mrb, mrb_value self) {
|
|
mrb_value addr, value;
|
|
mrb_get_args(mrb, "i|i", &addr, &value);
|
|
|
|
uint32_t addr_int = mrb_integer(addr);
|
|
uint16_t value_int = mrb_integer(value);
|
|
|
|
if (addr_int % 2 != 0) {
|
|
mrb_raise(mrb, E_ARGUMENT_ERROR, "Address must be 16bits aligned");
|
|
}
|
|
|
|
*(volatile uint16_t *)(addr_int) = value_int;
|
|
|
|
return self;
|
|
}
|
|
|
|
static mrb_value mrb_write8(mrb_state *mrb, mrb_value self) {
|
|
mrb_value addr, value;
|
|
mrb_get_args(mrb, "i|i", &addr, &value);
|
|
|
|
uint32_t addr_int = mrb_integer(addr);
|
|
uint16_t value_int = mrb_integer(value);
|
|
|
|
*(volatile uint8_t *)(addr_int) = value_int;
|
|
|
|
return self;
|
|
}
|
|
|
|
void mrb_mruby_devmem_gem_init(mrb_state *mrb) {
|
|
struct RClass *class_peekpoke = mrb_define_module(mrb, "Machine");
|
|
|
|
mrb_define_class_method(mrb, class_peekpoke, "read32", mrb_read32, MRB_ARGS_ARG(1, 0));
|
|
mrb_define_class_method(mrb, class_peekpoke, "read16", mrb_read16, MRB_ARGS_ARG(1, 0));
|
|
mrb_define_class_method(mrb, class_peekpoke, "read8", mrb_read8, MRB_ARGS_ARG(1, 0));
|
|
|
|
mrb_define_class_method(mrb, class_peekpoke, "write32", mrb_write32, MRB_ARGS_ARG(2, 0));
|
|
mrb_define_class_method(mrb, class_peekpoke, "write16", mrb_write16, MRB_ARGS_ARG(2, 0));
|
|
mrb_define_class_method(mrb, class_peekpoke, "write8", mrb_write8, MRB_ARGS_ARG(2, 0));
|
|
}
|
|
|
|
void mrb_mruby_devmem_gem_final(mrb_state *mrb) {
|
|
/* Not used */
|
|
} |