aboutsummaryrefslogtreecommitdiff
path: root/hw/misc/bcm2835_property.c
diff options
context:
space:
mode:
Diffstat (limited to 'hw/misc/bcm2835_property.c')
-rw-r--r--hw/misc/bcm2835_property.c98
1 files changed, 53 insertions, 45 deletions
diff --git a/hw/misc/bcm2835_property.c b/hw/misc/bcm2835_property.c
index 63de3db..a21c6a5 100644
--- a/hw/misc/bcm2835_property.c
+++ b/hw/misc/bcm2835_property.c
@@ -13,7 +13,7 @@
#include "hw/irq.h"
#include "hw/misc/bcm2835_mbox_defs.h"
#include "hw/arm/raspberrypi-fw-defs.h"
-#include "sysemu/dma.h"
+#include "system/dma.h"
#include "qemu/log.h"
#include "qemu/module.h"
#include "trace.h"
@@ -25,14 +25,7 @@
static void bcm2835_property_mbox_push(BCM2835PropertyState *s, uint32_t value)
{
- uint32_t tag;
- uint32_t bufsize;
uint32_t tot_len;
- size_t resplen;
- uint32_t tmp;
- int n;
- uint32_t offset, length, color;
- uint32_t start_num, number, otp_row;
/*
* Copy the current state of the framebuffer config; we will update
@@ -51,10 +44,10 @@ static void bcm2835_property_mbox_push(BCM2835PropertyState *s, uint32_t value)
/* @(addr + 4) : Buffer response code */
value = s->addr + 8;
while (value + 8 <= s->addr + tot_len) {
- tag = ldl_le_phys(&s->dma_as, value);
- bufsize = ldl_le_phys(&s->dma_as, value + 4);
+ uint32_t tag = ldl_le_phys(&s->dma_as, value);
+ uint32_t bufsize = ldl_le_phys(&s->dma_as, value + 4);
/* @(value + 8) : Request/response indicator */
- resplen = 0;
+ size_t resplen = 0;
switch (tag) {
case RPI_FWREQ_PROPERTY_END:
break;
@@ -98,13 +91,16 @@ static void bcm2835_property_mbox_push(BCM2835PropertyState *s, uint32_t value)
resplen = 8;
break;
case RPI_FWREQ_SET_POWER_STATE:
- /* Assume that whatever device they asked for exists,
- * and we'll just claim we set it to the desired state
+ {
+ /*
+ * Assume that whatever device they asked for exists,
+ * and we'll just claim we set it to the desired state.
*/
- tmp = ldl_le_phys(&s->dma_as, value + 16);
- stl_le_phys(&s->dma_as, value + 16, (tmp & 1));
+ uint32_t state = ldl_le_phys(&s->dma_as, value + 16);
+ stl_le_phys(&s->dma_as, value + 16, (state & 1));
resplen = 8;
break;
+ }
/* Clocks */
@@ -274,19 +270,25 @@ static void bcm2835_property_mbox_push(BCM2835PropertyState *s, uint32_t value)
resplen = 16;
break;
case RPI_FWREQ_FRAMEBUFFER_SET_PALETTE:
- offset = ldl_le_phys(&s->dma_as, value + 12);
- length = ldl_le_phys(&s->dma_as, value + 16);
- n = 0;
- while (n < length - offset) {
- color = ldl_le_phys(&s->dma_as, value + 20 + (n << 2));
- stl_le_phys(&s->dma_as,
- s->fbdev->vcram_base + ((offset + n) << 2), color);
- n++;
+ {
+ uint32_t offset = ldl_le_phys(&s->dma_as, value + 12);
+ uint32_t length = ldl_le_phys(&s->dma_as, value + 16);
+ int resp;
+
+ if (offset > 255 || length < 1 || length > 256) {
+ resp = 1; /* invalid request */
+ } else {
+ for (uint32_t e = 0; e < length; e++) {
+ uint32_t color = ldl_le_phys(&s->dma_as, value + 20 + (e << 2));
+ stl_le_phys(&s->dma_as,
+ s->fbdev->vcram_base + ((offset + e) << 2), color);
+ }
+ resp = 0;
}
- stl_le_phys(&s->dma_as, value + 12, 0);
+ stl_le_phys(&s->dma_as, value + 12, resp);
resplen = 4;
break;
-
+ }
case RPI_FWREQ_FRAMEBUFFER_GET_NUM_DISPLAYS:
stl_le_phys(&s->dma_as, value + 12, 1);
resplen = 4;
@@ -327,22 +329,25 @@ static void bcm2835_property_mbox_push(BCM2835PropertyState *s, uint32_t value)
/* Customer OTP */
case RPI_FWREQ_GET_CUSTOMER_OTP:
- start_num = ldl_le_phys(&s->dma_as, value + 12);
- number = ldl_le_phys(&s->dma_as, value + 16);
+ {
+ uint32_t start_num = ldl_le_phys(&s->dma_as, value + 12);
+ uint32_t number = ldl_le_phys(&s->dma_as, value + 16);
resplen = 8 + 4 * number;
- for (n = start_num; n < start_num + number &&
+ for (uint32_t n = start_num; n < start_num + number &&
n < BCM2835_OTP_CUSTOMER_OTP_LEN; n++) {
- otp_row = bcm2835_otp_get_row(s->otp,
+ uint32_t otp_row = bcm2835_otp_get_row(s->otp,
BCM2835_OTP_CUSTOMER_OTP + n);
stl_le_phys(&s->dma_as,
value + 20 + ((n - start_num) << 2), otp_row);
}
break;
+ }
case RPI_FWREQ_SET_CUSTOMER_OTP:
- start_num = ldl_le_phys(&s->dma_as, value + 12);
- number = ldl_le_phys(&s->dma_as, value + 16);
+ {
+ uint32_t start_num = ldl_le_phys(&s->dma_as, value + 12);
+ uint32_t number = ldl_le_phys(&s->dma_as, value + 16);
resplen = 4;
@@ -361,34 +366,37 @@ static void bcm2835_property_mbox_push(BCM2835PropertyState *s, uint32_t value)
break;
}
- for (n = start_num; n < start_num + number &&
+ for (uint32_t n = start_num; n < start_num + number &&
n < BCM2835_OTP_CUSTOMER_OTP_LEN; n++) {
- otp_row = ldl_le_phys(&s->dma_as,
+ uint32_t otp_row = ldl_le_phys(&s->dma_as,
value + 20 + ((n - start_num) << 2));
bcm2835_otp_set_row(s->otp,
BCM2835_OTP_CUSTOMER_OTP + n, otp_row);
}
break;
+ }
/* Device-specific private key */
-
case RPI_FWREQ_GET_PRIVATE_KEY:
- start_num = ldl_le_phys(&s->dma_as, value + 12);
- number = ldl_le_phys(&s->dma_as, value + 16);
+ {
+ uint32_t start_num = ldl_le_phys(&s->dma_as, value + 12);
+ uint32_t number = ldl_le_phys(&s->dma_as, value + 16);
resplen = 8 + 4 * number;
- for (n = start_num; n < start_num + number &&
+ for (uint32_t n = start_num; n < start_num + number &&
n < BCM2835_OTP_PRIVATE_KEY_LEN; n++) {
- otp_row = bcm2835_otp_get_row(s->otp,
+ uint32_t otp_row = bcm2835_otp_get_row(s->otp,
BCM2835_OTP_PRIVATE_KEY + n);
stl_le_phys(&s->dma_as,
value + 20 + ((n - start_num) << 2), otp_row);
}
break;
+ }
case RPI_FWREQ_SET_PRIVATE_KEY:
- start_num = ldl_le_phys(&s->dma_as, value + 12);
- number = ldl_le_phys(&s->dma_as, value + 16);
+ {
+ uint32_t start_num = ldl_le_phys(&s->dma_as, value + 12);
+ uint32_t number = ldl_le_phys(&s->dma_as, value + 16);
resplen = 4;
@@ -398,14 +406,15 @@ static void bcm2835_property_mbox_push(BCM2835PropertyState *s, uint32_t value)
break;
}
- for (n = start_num; n < start_num + number &&
+ for (uint32_t n = start_num; n < start_num + number &&
n < BCM2835_OTP_PRIVATE_KEY_LEN; n++) {
- otp_row = ldl_le_phys(&s->dma_as,
+ uint32_t otp_row = ldl_le_phys(&s->dma_as,
value + 20 + ((n - start_num) << 2));
bcm2835_otp_set_row(s->otp,
BCM2835_OTP_PRIVATE_KEY + n, otp_row);
}
break;
+ }
default:
qemu_log_mask(LOG_UNIMP,
"bcm2835_property: unhandled tag 0x%08x\n", tag);
@@ -542,13 +551,12 @@ static void bcm2835_property_realize(DeviceState *dev, Error **errp)
bcm2835_property_reset(dev);
}
-static Property bcm2835_property_props[] = {
+static const Property bcm2835_property_props[] = {
DEFINE_PROP_UINT32("board-rev", BCM2835PropertyState, board_rev, 0),
DEFINE_PROP_STRING("command-line", BCM2835PropertyState, command_line),
- DEFINE_PROP_END_OF_LIST()
};
-static void bcm2835_property_class_init(ObjectClass *klass, void *data)
+static void bcm2835_property_class_init(ObjectClass *klass, const void *data)
{
DeviceClass *dc = DEVICE_CLASS(klass);