1

I have been working on a bare metal program on my Raspberry Pi 3 B and am currently working on using the Mailbox Property Interface. I have been able to use it to initialize a framebuffer using the following request:

[
                //Headers: message size and type
                35 * 4,
                MBOX_REQUEST,
                Tag::SetPhyDim as u32,
                8,
                8,
                1920,
                1080,
                Tag::SetVirDim as u32,
                8,
                8,
                1920,
                1080,
                Tag::SetVirOff as u32,
                8,
                8,
                0,
                0,
                Tag::SetDepth as u32,
                4,
                4,
                32,
                Tag::SetPxlOrdr as u32,
                4,
                4,
                1,
                Tag::GetFB as u32,
                8,
                8,
                4096,
                0,
                Tag::GetPitch as u32,
                4,
                4,
                0,
                Tag::EndOfMessage as u32,
                0,
            ]

I have tried using other requests, such as 0x10001, which should return the board model number. The formatted request is:

[
    32,
    MBOX_REQUEST,
    0x1001,
    0, //Request Length
    0, //Request Length
    Tag::EndOfMessage as u32
]

When I send this message this is the response, which doesn't have the requested information: [32, 0x80000000, 0x10001, 0, 0x80000004, 0]

Here is how I send the message:

    println!("Testing Message Buffer");
    let mut mb = MessageBuffer::new();
    println!(
        "Message Buffer Acquired At: {:#x}",
        &mb as *const MessageBuffer as usize
    );
    mb.data[0] = 32;
    mb.data[1] = 0; //Req
    mb.data[2] = 0x10001;
    mb.data[3] = 0;
    mb.data[4] = 0;
    mb.data[5] = 0;
let val = mailbox.call(&mb as *const MessageBuffer as u32, Channel::Prop) & !0b1111;
println!("Message Received at {:#x}: {:?}", val, unsafe {
    core::slice::from_raw_parts(val as *const u32, 64)
});

On my boot disk, I did delete all of the device tree files. Could this be part of the issue?

Any help would be appreciated.

Someone
  • 111
  • 1

1 Answers1

1

The VideoCore mailbox protocol is downright awful, I've just dredged through it myself. The issue is that you are not forming your requests correctly.

Here's the actual grammar for messages:

[
uint32_t message_length,
uint32_t message_type,
/* tag buffer begin */
    /* tag */
    {
    uint32_t tag;
    // the amount of space you ACTUALLY have
    uint32_t buffer_length; 
    // set to zero. VC sets this to (1<<31) | <the length of the message it WANTED to send>
    // note that this may be greater than `buffer_length`!!!
    uint32_t response_length;
    // your response data is placed here
    uint32_t buffer[buffer_length / sizeof(uint32_t)]
    }, /* repeat as many times as you like */
/* tag buffer end */
uint32_t end_of_message_marker
]

The issue you were seeing with this packet:

[
    32,/* length */
    MBOX_REQUEST, /* type */
    0x1001, /* tag */
    0, /* buffer length */
    0, /* response length */
    Tag::EndOfMessage as u32
]

is that you are telling the VC that you have 0 bytes of buffer space and thus the VC cannot send you any data. We see this in the response:

[
32, /* length */
0x80000000, /* type */
0x10001, /* tag */
0, /* buffer length */
0x80000004, /* (1<<31) | <length VC wanted to send> */
0 /* terminate */
]

where the VC tells us that it wanted to send 4 bytes but, in reality, it was only able to send MIN(buffer_length, response_length & ~(1<<31)). The following packet should work:

[
    36,/* length */
    MBOX_REQUEST, /* type */
    0x1001, /* tag */
    4, /* buffer length */
    0, /* response length */
    0, /* buffer */
    Tag::EndOfMessage as u32
]
Allison
  • 121
  • 4