This adds a sandbox mailbox implementation (provider), a test client device, instantiates them both from Sandbox's DT, and adds a DM test that excercises everything. Signed-off-by: Stephen Warren <swarren@nvidia.com> Acked-by: Simon Glass <sjg@chromium.org> # v1master
parent
6238935d01
commit
8961b52424
@ -0,0 +1,21 @@ |
|||||||
|
/*
|
||||||
|
* Copyright (c) 2016, NVIDIA CORPORATION. |
||||||
|
* |
||||||
|
* SPDX-License-Identifier: GPL-2.0 |
||||||
|
*/ |
||||||
|
|
||||||
|
#ifndef __SANDBOX_MBOX_H |
||||||
|
#define __SANDBOX_MBOX_H |
||||||
|
|
||||||
|
#include <common.h> |
||||||
|
|
||||||
|
#define SANDBOX_MBOX_PING_XOR 0x12345678 |
||||||
|
|
||||||
|
struct udevice; |
||||||
|
|
||||||
|
int sandbox_mbox_test_get(struct udevice *dev); |
||||||
|
int sandbox_mbox_test_send(struct udevice *dev, uint32_t msg); |
||||||
|
int sandbox_mbox_test_recv(struct udevice *dev, uint32_t *msg); |
||||||
|
int sandbox_mbox_test_free(struct udevice *dev); |
||||||
|
|
||||||
|
#endif |
@ -0,0 +1,54 @@ |
|||||||
|
/*
|
||||||
|
* Copyright (c) 2016, NVIDIA CORPORATION. |
||||||
|
* |
||||||
|
* SPDX-License-Identifier: GPL-2.0 |
||||||
|
*/ |
||||||
|
|
||||||
|
#include <common.h> |
||||||
|
#include <dm.h> |
||||||
|
#include <mailbox_client.h> |
||||||
|
#include <asm/io.h> |
||||||
|
|
||||||
|
struct sandbox_mbox_test { |
||||||
|
struct mbox_chan chan; |
||||||
|
}; |
||||||
|
|
||||||
|
int sandbox_mbox_test_get(struct udevice *dev) |
||||||
|
{ |
||||||
|
struct sandbox_mbox_test *sbmt = dev_get_priv(dev); |
||||||
|
|
||||||
|
return mbox_get_by_name(dev, "test", &sbmt->chan); |
||||||
|
} |
||||||
|
|
||||||
|
int sandbox_mbox_test_send(struct udevice *dev, uint32_t msg) |
||||||
|
{ |
||||||
|
struct sandbox_mbox_test *sbmt = dev_get_priv(dev); |
||||||
|
|
||||||
|
return mbox_send(&sbmt->chan, &msg); |
||||||
|
} |
||||||
|
|
||||||
|
int sandbox_mbox_test_recv(struct udevice *dev, uint32_t *msg) |
||||||
|
{ |
||||||
|
struct sandbox_mbox_test *sbmt = dev_get_priv(dev); |
||||||
|
|
||||||
|
return mbox_recv(&sbmt->chan, msg, 100); |
||||||
|
} |
||||||
|
|
||||||
|
int sandbox_mbox_test_free(struct udevice *dev) |
||||||
|
{ |
||||||
|
struct sandbox_mbox_test *sbmt = dev_get_priv(dev); |
||||||
|
|
||||||
|
return mbox_free(&sbmt->chan); |
||||||
|
} |
||||||
|
|
||||||
|
static const struct udevice_id sandbox_mbox_test_ids[] = { |
||||||
|
{ .compatible = "sandbox,mbox-test" }, |
||||||
|
{ } |
||||||
|
}; |
||||||
|
|
||||||
|
U_BOOT_DRIVER(sandbox_mbox_test) = { |
||||||
|
.name = "sandbox_mbox_test", |
||||||
|
.id = UCLASS_MISC, |
||||||
|
.of_match = sandbox_mbox_test_ids, |
||||||
|
.priv_auto_alloc_size = sizeof(struct sandbox_mbox_test), |
||||||
|
}; |
@ -0,0 +1,104 @@ |
|||||||
|
/*
|
||||||
|
* Copyright (c) 2016, NVIDIA CORPORATION. |
||||||
|
* |
||||||
|
* SPDX-License-Identifier: GPL-2.0 |
||||||
|
*/ |
||||||
|
|
||||||
|
#include <common.h> |
||||||
|
#include <dm.h> |
||||||
|
#include <mailbox_uclass.h> |
||||||
|
#include <asm/io.h> |
||||||
|
#include <asm/mbox.h> |
||||||
|
|
||||||
|
#define SANDBOX_MBOX_CHANNELS 2 |
||||||
|
|
||||||
|
struct sandbox_mbox_chan { |
||||||
|
bool rx_msg_valid; |
||||||
|
uint32_t rx_msg; |
||||||
|
}; |
||||||
|
|
||||||
|
struct sandbox_mbox { |
||||||
|
struct sandbox_mbox_chan chans[SANDBOX_MBOX_CHANNELS]; |
||||||
|
}; |
||||||
|
|
||||||
|
static int sandbox_mbox_request(struct mbox_chan *chan) |
||||||
|
{ |
||||||
|
debug("%s(chan=%p)\n", __func__, chan); |
||||||
|
|
||||||
|
if (chan->id >= SANDBOX_MBOX_CHANNELS) |
||||||
|
return -EINVAL; |
||||||
|
|
||||||
|
return 0; |
||||||
|
} |
||||||
|
|
||||||
|
static int sandbox_mbox_free(struct mbox_chan *chan) |
||||||
|
{ |
||||||
|
debug("%s(chan=%p)\n", __func__, chan); |
||||||
|
|
||||||
|
return 0; |
||||||
|
} |
||||||
|
|
||||||
|
static int sandbox_mbox_send(struct mbox_chan *chan, const void *data) |
||||||
|
{ |
||||||
|
struct sandbox_mbox *sbm = dev_get_priv(chan->dev); |
||||||
|
const uint32_t *pmsg = data; |
||||||
|
|
||||||
|
debug("%s(chan=%p, data=%p)\n", __func__, chan, data); |
||||||
|
|
||||||
|
sbm->chans[chan->id].rx_msg = *pmsg ^ SANDBOX_MBOX_PING_XOR; |
||||||
|
sbm->chans[chan->id].rx_msg_valid = true; |
||||||
|
|
||||||
|
return 0; |
||||||
|
} |
||||||
|
|
||||||
|
static int sandbox_mbox_recv(struct mbox_chan *chan, void *data) |
||||||
|
{ |
||||||
|
struct sandbox_mbox *sbm = dev_get_priv(chan->dev); |
||||||
|
uint32_t *pmsg = data; |
||||||
|
|
||||||
|
debug("%s(chan=%p, data=%p)\n", __func__, chan, data); |
||||||
|
|
||||||
|
if (!sbm->chans[chan->id].rx_msg_valid) |
||||||
|
return -ENODATA; |
||||||
|
|
||||||
|
*pmsg = sbm->chans[chan->id].rx_msg; |
||||||
|
sbm->chans[chan->id].rx_msg_valid = false; |
||||||
|
|
||||||
|
return 0; |
||||||
|
} |
||||||
|
|
||||||
|
static int sandbox_mbox_bind(struct udevice *dev) |
||||||
|
{ |
||||||
|
debug("%s(dev=%p)\n", __func__, dev); |
||||||
|
|
||||||
|
return 0; |
||||||
|
} |
||||||
|
|
||||||
|
static int sandbox_mbox_probe(struct udevice *dev) |
||||||
|
{ |
||||||
|
debug("%s(dev=%p)\n", __func__, dev); |
||||||
|
|
||||||
|
return 0; |
||||||
|
} |
||||||
|
|
||||||
|
static const struct udevice_id sandbox_mbox_ids[] = { |
||||||
|
{ .compatible = "sandbox,mbox" }, |
||||||
|
{ } |
||||||
|
}; |
||||||
|
|
||||||
|
struct mbox_ops sandbox_mbox_mbox_ops = { |
||||||
|
.request = sandbox_mbox_request, |
||||||
|
.free = sandbox_mbox_free, |
||||||
|
.send = sandbox_mbox_send, |
||||||
|
.recv = sandbox_mbox_recv, |
||||||
|
}; |
||||||
|
|
||||||
|
U_BOOT_DRIVER(sandbox_mbox) = { |
||||||
|
.name = "sandbox_mbox", |
||||||
|
.id = UCLASS_MAILBOX, |
||||||
|
.of_match = sandbox_mbox_ids, |
||||||
|
.bind = sandbox_mbox_bind, |
||||||
|
.probe = sandbox_mbox_probe, |
||||||
|
.priv_auto_alloc_size = sizeof(struct sandbox_mbox), |
||||||
|
.ops = &sandbox_mbox_mbox_ops, |
||||||
|
}; |
@ -0,0 +1,31 @@ |
|||||||
|
/*
|
||||||
|
* Copyright (c) 2016, NVIDIA CORPORATION. |
||||||
|
* |
||||||
|
* SPDX-License-Identifier: GPL-2.0 |
||||||
|
*/ |
||||||
|
|
||||||
|
#include <common.h> |
||||||
|
#include <dm.h> |
||||||
|
#include <dm/test.h> |
||||||
|
#include <asm/mbox.h> |
||||||
|
#include <test/ut.h> |
||||||
|
|
||||||
|
static int dm_test_mailbox(struct unit_test_state *uts) |
||||||
|
{ |
||||||
|
struct udevice *dev; |
||||||
|
uint32_t msg; |
||||||
|
|
||||||
|
ut_assertok(uclass_get_device_by_name(UCLASS_MISC, "mbox-test", &dev)); |
||||||
|
ut_assertok(sandbox_mbox_test_get(dev)); |
||||||
|
|
||||||
|
ut_asserteq(-ETIMEDOUT, sandbox_mbox_test_recv(dev, &msg)); |
||||||
|
ut_assertok(sandbox_mbox_test_send(dev, 0xaaff9955UL)); |
||||||
|
ut_assertok(sandbox_mbox_test_recv(dev, &msg)); |
||||||
|
ut_asserteq(msg, 0xaaff9955UL ^ SANDBOX_MBOX_PING_XOR); |
||||||
|
ut_asserteq(-ETIMEDOUT, sandbox_mbox_test_recv(dev, &msg)); |
||||||
|
|
||||||
|
ut_assertok(sandbox_mbox_test_free(dev)); |
||||||
|
|
||||||
|
return 0; |
||||||
|
} |
||||||
|
DM_TEST(dm_test_mailbox, DM_TESTF_SCAN_FDT); |
Loading…
Reference in new issue