Str "-Wno-format"
]
-cFlags = ArchDefaults.commonCFlags
+cFlags = ArchDefaults.commonCFlags
++ ArchDefaults.commonFlags
++ ourCommonFlags
stdLibs = ArchDefaults.stdLibs arch
-options = (ArchDefaults.options arch archFamily) {
+options = (ArchDefaults.options arch archFamily) {
optFlags = cFlags,
optCxxFlags = cxxFlags,
optDefines = cDefines,
- optDependencies =
+ optDependencies =
[ PreDep InstallTree arch "/include/trace_definitions/trace_defs.h",
PreDep InstallTree arch "/include/errors/errno.h",
PreDep InstallTree arch "/include/barrelfish_kpi/capbits.h",
optLdFlags = ldFlags,
optLdCxxFlags = ldCxxFlags,
optLibs = stdLibs,
- optInterconnectDrivers = ["lmp", "ump"],
- optFlounderBackends = ["lmp", "ump"]
+ optInterconnectDrivers = ["lmp", "ump", "local"],
+ optFlounderBackends = ["lmp", "ump", "local"]
}
--
(ArchDefaults.kernelLibs arch)
),
-- Generate kernel assembly dump
- Rule [ Str objdump,
- Str "-d",
+ Rule [ Str objdump,
+ Str "-d",
Str "-M reg-names-raw",
- In BuildTree arch kbinary,
+ In BuildTree arch kbinary,
Str ">", Out arch kasmdump ],
Rule [ Str "cpp",
NStr "-I", NoDep SrcTree "src" "/kernel/include/arch/armv7",
Str "-Wno-format"
]
-cFlags = ArchDefaults.commonCFlags
+cFlags = ArchDefaults.commonCFlags
++ ArchDefaults.commonFlags
++ ourCommonFlags
stdLibs = ArchDefaults.stdLibs arch
-options = (ArchDefaults.options arch archFamily) {
+options = (ArchDefaults.options arch archFamily) {
optFlags = cFlags,
optCxxFlags = cxxFlags,
optDefines = cDefines,
- optDependencies =
+ optDependencies =
[ PreDep InstallTree arch "/include/trace_definitions/trace_defs.h",
PreDep InstallTree arch "/include/errors/errno.h",
PreDep InstallTree arch "/include/barrelfish_kpi/capbits.h",
optLdFlags = ldFlags,
optLdCxxFlags = ldCxxFlags,
optLibs = stdLibs,
- optInterconnectDrivers = ["lmp", "ump"],
- optFlounderBackends = ["lmp", "ump"]
+ optInterconnectDrivers = ["lmp", "ump", "local"],
+ optFlounderBackends = ["lmp", "ump", "local"]
}
--
Rules [ Rule ([ Str compiler ] ++
map Str Config.cOptFlags ++
[ NStr "-T", In BuildTree arch linkscript,
- Str "-o",
+ Str "-o",
Out arch kfull,
NStr "-Wl,-Map,", Out arch kernelmap
]
Rule $ strip opts kfull kdebug kbinary,
Rule $ debug opts kfull kdebug,
-- Generate kernel assembly dump
- Rule [ Str objdump,
- Str "-d",
+ Rule [ Str objdump,
+ Str "-d",
Str "-M reg-names-raw",
- In BuildTree arch kbinary,
- Str ">",
+ In BuildTree arch kbinary,
+ Str ">",
Out arch kasmdump ],
Rule [ Str "cpp",
NStr "-I", NoDep SrcTree "src" "/kernel/include/arch/armv8",
-- Architectural definitions for Barrelfish on x86_mic.
--
-- This architecture is used to build for the Intel Xeon Phi architecture.
---
+--
--------------------------------------------------------------------------
module K1om where
ourCommonFlags = [ Str "-m64",
Str "-mno-red-zone",
Str "-fPIE",
- Str "-fno-stack-protector",
+ Str "-fno-stack-protector",
Str "-Wno-unused-but-set-variable",
Str "-Wno-packed-bitfield-compat",
Str "-fno-tree-vectorize",
Str "-mno-sse4.2",
Str "-mno-sse4",
Str "-mno-sse4a",
- Str "-mno-3dnow",
+ Str "-mno-3dnow",
-- Apparently the MPSS gcc somehow incudes CMOVES?
Str "-fno-if-conversion",
-- specific Xeon Phi architecture
-- adding x86_64 includes to the K1OM architecture
kernelOptIncludes = [NoDep SrcTree "src" ("/kernel/include/arch/x86_64"),
- NoDep SrcTree "src" ("/include/target/x86_64"),
- NoDep SrcTree "src" ("/include/arch/x86_64")]
+ NoDep SrcTree "src" ("/include/target/x86_64"),
+ NoDep SrcTree "src" ("/include/arch/x86_64")]
-options = (ArchDefaults.options arch archFamily) {
+options = (ArchDefaults.options arch archFamily) {
optFlags = cFlags,
optCxxFlags = cxxFlags,
optDefines = cDefines,
optLdFlags = ldFlags,
optLdCxxFlags = ldCxxFlags,
- optInterconnectDrivers = ["lmp", "ump", "multihop"],
- optFlounderBackends = ["lmp", "ump", "multihop"],
+ optInterconnectDrivers = ["lmp", "ump", "multihop", "local"],
+ optFlounderBackends = ["lmp", "ump", "multihop", "local"],
optIncludes = ArchDefaults.cStdIncs arch archFamily
++
- [NoDep SrcTree "src" ("/include/target/x86_64"),
+ [NoDep SrcTree "src" ("/include/target/x86_64"),
NoDep SrcTree "src" ("/include/arch/x86_64")]
}
"-nostdinc",
"-std=c99",
"-m64",
- "-fPIE",
+ "-fPIE",
"-e start",
"-mno-red-zone",
"-Wa,-march=k1om",
"-mno-sse4.2",
"-mno-sse4",
"-mno-sse4a",
- "-mno-3dnow",
+ "-mno-3dnow",
-- Apparently the MPSS gcc somehow incudes CMOVES?
"-fno-if-conversion" ] ]
--
-- Link the kernel (CPU Driver)
---
+--
linkKernel :: Options -> [String] -> [String] -> String -> HRule
-linkKernel opts objs libs kbin =
+linkKernel opts objs libs kbin =
let linkscript = "/kernel/linker.lds"
in
Rules [ Rule ([ Str compiler ] ++
map Str Config.cOptFlags ++
[ NStr "-T", In BuildTree arch "/kernel/linker.lds",
- Str "-o", Out arch kbin
+ Str "-o", Out arch kbin
]
++ (optLdFlags opts)
++
[ In BuildTree arch o | o <- objs ]
++
[ In BuildTree arch l | l <- libs ]
- ++
+ ++
[ NL, NStr "echo -e '\\0002' | dd of=",
- Out arch kbin,
+ Out arch kbin,
Str "bs=1 seek=16 count=1 conv=notrunc status=noxfer"
]
),
- Rule [ Str "cpp",
+ Rule [ Str "cpp",
NStr "-I", NoDep SrcTree "src" "/kernel/include/",
- Str "-D__ASSEMBLER__",
+ Str "-D__ASSEMBLER__",
Str "-P", In SrcTree "src" "/kernel/arch/k1om/linker.lds.in",
- Out arch linkscript
+ Out arch linkscript
],
-- Produce a stripped binary
Rule [ Str objcopy,
"descq",
"ddomain",
"dcontrol",
- "net_filter"
+ "net_filter",
+ "twl6030",
+ "cm2"
],
arch <- allArchitectures
] ++
--- /dev/null
+interface cm2 "Controlling CM2" {
+ rpc enable_i2c(in uint32 index);
+ rpc enable_hsmmc1();
+ rpc get_hsmmc1_base_clock(out uint32 clock);
+};
*/
rpc create(in char cls[clen, 256], in char name[nlen, 256],
in char a1[a1len, 256], in char a2[a2len, 256], in char a3[a3len, 256], in char a4[a4len, 256],
- in cap cap1, in cap cap2, in cap cap3, in cap cap4, in uint64 flags,
+ in cap cap1, in cap cap2, in cap cap3, in cap cap4, in cap cap5, in cap cap6, in uint64 flags,
out iref devif, out iref control, out errval err);
/**
* Destroys a driver inside a domain.
--- /dev/null
+interface twl6030 "Controlling the Fully Integrated Power Management IC" {
+ rpc vmmc_on();
+ rpc vmmc_off();
+ rpc vmmc_vsel(in uint32 millis);
+};
#include <barrelfish/types.h>
#include <errors/errno.h>
+#include <collections/list.h>
struct bfdriver;
struct bfdriver* driverkit_lookup_cls(const char*);
/** driver domain flounder interface */
+struct domain_instance {
+ uint64_t service_id;
+ collections_listnode* to_spawn;
+ collections_listnode* spawned;
+ struct ddomain_binding *b;
+};
+
+struct driver_instance {
+ char* driver_name;
+ char* inst_name;
+ char** args;
+ size_t cap_idx;
+ struct capref* caps;
+ uint64_t flags;
+ iref_t dev;
+ iref_t control;
+};
errval_t ddomain_communication_init(iref_t kaluga_iref, uint64_t id);
errval_t ddomain_controller_init(void);
struct domain_instance* ddomain_create_domain_instance(uint64_t id);
void ddomain_free_driver_inst(void* arg);
void ddomain_free_domain_inst(void* arg);
errval_t ddomain_driver_add_cap(struct driver_instance* drv, struct capref cap);
+void ddomain_wait_for_id(void);
/** driver control flounder interface */
errval_t dcontrol_service_init(struct bfdriver_instance* bfi, struct waitset* ws);
errval_t map_device_register(lpaddr_t, size_t, lvaddr_t*);
errval_t map_device_cap(struct capref, lvaddr_t *);
+errval_t driverkit_local_service_register(char* name, void* tbl);
+void* driverkit_local_service_lookup(char* name);
#define __bfdrivers __attribute__((__section__(".bfdrivers")))
#define __visible __attribute__((__externally_visible__))
/// Enqueue a chanstate on a queue
static void enqueue(struct waitset_chanstate **queue, struct waitset_chanstate *chan)
{
+ assert(chan != NULL);
+ if (queue == (void*)0x8) {
+ printf("callstack: %zu %p %p\n",
+ __builtin_return_address(0));
+ }
+
if (*queue == NULL) {
*queue = chan;
chan->next = chan->prev = chan;
assert(bfi->name != NULL);
if (err_is_fail(err)) {
- DRIVERKIT_DEBUG("Exporting control interface for %s failed.", bfi->name);
+ DRIVERKIT_DEBUG("Exporting control interface for %s failed.\n", bfi->name);
err = err_push(err, DRIVERKIT_ERR_CONTROL_IFACE_EXPORT);
}
else {
assert (r > 0);
err = nameservice_register(service_name, iref);
if (err_is_fail(err)) {
- DEBUG_ERR(err, "Can't register control interface with nameserver.");
+ DEBUG_ERR(err, "Can't register control interface with nameserver.\n");
err = err_push(err, DRIVERKIT_ERR_CONTROL_IFACE_EXPORT);
}
else {
static errval_t rpc_connect_cb(void *st, struct dcontrol_binding *b)
{
struct bfdriver_instance* bfi = (struct bfdriver_instance*) st;
+ assert(bfi != NULL);
+
DRIVERKIT_DEBUG("Got a new connection for controlling driver instance %s.\n", bfi->name);
b->rx_vtbl = rpc_rx_vtbl;
b->st = st;
#include <driverkit/driverkit.h>
#include <if/ddomain_defs.h>
-#include <collections/list.h>
-
#include "debug.h"
#define SERVICE_NAME "ddomain_controller"
-static collections_listnode* driver_domain_instances;
-
-struct domain_instance {
- uint64_t service_id;
- struct ddomain_binding *b;
- collections_listnode* to_spawn;
- collections_listnode* spawned;
-};
+#define MAX_CAPS 6
+#define MAX_ARGS 4
-struct driver_instance {
- char* driver_name;
- char* inst_name;
- char** args;
- size_t cap_idx;
- struct capref* caps;
- uint64_t flags;
- iref_t dev;
- iref_t control;
-};
+static collections_listnode* driver_domain_instances;
void ddomain_free_driver_inst(void* arg) {
struct driver_instance* di = (struct driver_instance*) arg;
struct domain_instance* ddomain_create_domain_instance(uint64_t id) {
struct domain_instance* di = calloc(1, sizeof(struct domain_instance));
assert(di != NULL);
+ di->b = NULL;
di->service_id = id;
collections_list_create(&di->to_spawn, ddomain_free_driver_inst);
collections_list_create(&di->spawned, ddomain_free_driver_inst);
di->inst_name = strdup(inst_name);
assert(di->inst_name);
- di->args = calloc(sizeof(char*), 4);
+ di->args = calloc(sizeof(char*), MAX_ARGS);
assert(di->args);
- di->caps = calloc(sizeof(struct capref), 4);
+ di->caps = calloc(sizeof(struct capref), MAX_CAPS);
assert(di->caps);
return di;
errval_t ddomain_driver_add_cap(struct driver_instance* drv, struct capref cap) {
assert(drv != NULL);
- if (drv->cap_idx < 4) {
+ if (drv->cap_idx < MAX_CAPS) {
drv->caps[drv->cap_idx++] = cap;
return SYS_ERR_OK;
}
assert(drv != NULL);
errval_t out_err = SYS_ERR_OK;
- errval_t err = b->rpc_tx_vtbl.create(b, drv->driver_name, strlen(drv->driver_name),
- drv->inst_name, strlen(drv->inst_name),
+ DRIVERKIT_DEBUG("Trying to spawn %s (named %s)\n", drv->driver_name, drv->inst_name);
+ errval_t err = b->rpc_tx_vtbl.create(b, drv->driver_name, strlen(drv->driver_name)+1,
+ drv->inst_name, strlen(drv->inst_name)+1,
drv->args[0], (drv->args[0] != NULL) ? strlen(drv->args[0]) : 0,
drv->args[1], (drv->args[1] != NULL) ? strlen(drv->args[1]) : 0,
drv->args[2], (drv->args[2] != NULL) ? strlen(drv->args[2]) : 0,
drv->args[3], (drv->args[3] != NULL) ? strlen(drv->args[3]) : 0,
- drv->caps[0], drv->caps[1], drv->caps[2], drv->caps[3],
- drv->flags, &out_err, &drv->dev, &drv->control);
-
- DRIVERKIT_DEBUG("Driver domain created driver reachable at [%"PRIuIREF", %"PRIuIREF"]\n", drv->dev, drv->control);
+ drv->caps[0], drv->caps[1], drv->caps[2], drv->caps[3], drv->caps[4], drv->caps[5],
+ drv->flags, &drv->dev, &drv->control, &out_err);
if (err_is_fail(err)) {
+ DEBUG_ERR(err, "Failed to create driver %s\n", drv->driver_name);
return err;
}
else {
+ printf("Driver %s created, reachable at [%"PRIuIREF", %"PRIuIREF"]\n", drv->driver_name, drv->dev, drv->control);
return out_err;
}
}
static int32_t find_id(void* data, void* arg) {
struct domain_instance* di = (void*) data;
uint64_t id = (uint64_t)(uintptr_t) arg;
- printf("%s:%s:%d: check %"PRIu64"\n", __FILE__, __FUNCTION__, __LINE__, di->service_id);
return di->service_id == id;
}
void* found = collections_list_find_if(driver_domain_instances, find_id, (void*)(uintptr_t) id);
if (found) {
- DRIVERKIT_DEBUG("Found driver for id %"PRIu64"", id);
+ DRIVERKIT_DEBUG("Found driver for id %"PRIu64"\n", id);
struct domain_instance* di = (struct domain_instance*) found;
assert(di->service_id == id);
di->b = binding;
void* removed;
while ( (removed = collections_list_remove_ith_item(di->to_spawn, 0)) != NULL ) {
struct driver_instance* driver = (struct driver_instance*) removed;
- DRIVERKIT_DEBUG("Trying to spawn %s", driver->inst_name);
+ DRIVERKIT_DEBUG("Trying to spawn %s\n", driver->inst_name);
errval_t err = create_call(di->b, driver);
if (err_is_fail(err)) {
DEBUG_ERR(err, "Can't spawn driver intstance.");
static errval_t rpc_connect_cb(void *st, struct ddomain_binding *b)
{
- DRIVERKIT_DEBUG("Got a new connection from driver domain.\n");
+ DRIVERKIT_DEBUG("%s:%s:%d: Got a new connection from driver domain.\n", __FILE__, __FUNCTION__, __LINE__);
rpc_export.b = b;
b->rx_vtbl = rpc_rx_vtbl;
return err;
}
+ DRIVERKIT_DEBUG("%s:%s:%d: Trying to export ddomain interface\n", __FILE__, __FUNCTION__, __LINE__);
// XXX: broken
while (!rpc_export.is_done) {
messages_wait_and_handle_next();
*/
static void create_handler(struct ddomain_binding* binding, const char* cls, size_t cls_len,
const char* name, size_t nlen,
- const char* a1, size_t a1len, const char* a2, size_t a2len, const char* a3, size_t a3len, const char* a4, size_t a4len,
- struct capref cap1, struct capref cap2, struct capref cap3, struct capref cap4,
+ const char* a1, size_t a1len, const char* a2, size_t a2len,
+ const char* a3, size_t a3len, const char* a4, size_t a4len,
+ struct capref cap1, struct capref cap2, struct capref cap3,
+ struct capref cap4, struct capref cap5, struct capref cap6,
uint64_t flags) {
DRIVERKIT_DEBUG("Driver domain got create message from kaluga for %s\n", cls);
iref_t dev = 0, ctrl = 0;
+ static size_t NR_CAPS = 6;
+ static size_t NR_ARGS = 4;
+
// This array is owned by the driver after create:
- struct capref* cap_array = calloc(sizeof(struct capref), 4);
+ struct capref* cap_array = calloc(sizeof(struct capref), NR_CAPS);
cap_array[0] = cap1;
cap_array[1] = cap2;
cap_array[2] = cap3;
cap_array[3] = cap4;
+ cap_array[4] = cap5;
+ cap_array[5] = cap6;
char** args_array = calloc(sizeof(char*), 4);
args_array[0] = a1 != NULL ? strdup(a1) : NULL;
args_array[2] = a3 != NULL ? strdup(a3) : NULL;
args_array[3] = a4 != NULL ? strdup(a4) : NULL;
- errval_t err = driverkit_create_driver(cls, name, cap_array, 4, args_array, 4, flags, &dev, &ctrl);
+ DRIVERKIT_DEBUG("Instantiate driver\n");
+ errval_t err = driverkit_create_driver(cls, name, cap_array, NR_CAPS, args_array, NR_ARGS, flags, &dev, &ctrl);
if (err_is_fail(err)) {
DEBUG_ERR(err, "Instantiating driver failed, report this back to Kaluga.\n");
}
- err = binding->tx_vtbl.create_response(binding, NOP_CONT, dev, ctrl, err);
+ DRIVERKIT_DEBUG("sending create response to kaluga\n");
+ err = ddomain_create_response__tx(binding, NOP_CONT, dev, ctrl, err);
if (err_is_fail(err)) {
USER_PANIC_ERR(err, "Sending reply failed.\n");
}
if (err_is_fail(err)) {
return err;
}
-
+ DRIVERKIT_DEBUG("%s:%s:%d: Trying to connect to kaluga...\n", __FILE__, __FUNCTION__, __LINE__);
// XXX: broken
while (!rpc_bind.is_done) {
messages_wait_and_handle_next();
}
- printf("%s:%s:%d: SEND IDENTIFY\n", __FILE__, __FUNCTION__, __LINE__);
+ DRIVERKIT_DEBUG("%s:%s:%d: Send identify %"PRIu64"\n", __FILE__, __FUNCTION__, __LINE__, ident);
errval_t send_err = rpc_bind.binding->tx_vtbl.identify(rpc_bind.binding, NOP_CONT, ident);
assert(err_is_ok(send_err));
#ifndef __DRIVERKIT_DEBUG__
#define __DRIVERKIT_DEBUG__
-#define ENABLE_DRIVERKIT_DEBUG 1
+//#define ENABLE_DRIVERKIT_DEBUG 1
#if defined(ENABLE_DRIVERKIT_DEBUG) || defined(GLOBAL_DEBUG)
-#define DRIVERKIT_DEBUG(x...) printf("[dkit] " x)
+#define DRIVERKIT_DEBUG(x...) debug_printf("[dkit] " x)
#else
#define DRIVERKIT_DEBUG(x...) ((void)0)
#endif
return err;
}
+
+
+errval_t driverkit_local_service_register(char* name, void* tbl)
+{
+
+ return SYS_ERR_OK;
+}
+
+void* driverkit_local_service_lookup(char* name)
+{
+
+ return NULL;
+}
cFiles = [ "main.c"],
addLinkFlags = ["-T" ++ Config.source_dir ++ "/lib/driverkit/bfdrivers.ld" ],
addLibraries = libDeps [ "driverkit", "thc" ],
- addModules = ["drivermodule", "fdif_module", "sdma_module", "mmchs_module"]
-
+ addModules = ["fdif_module", "sdma_module", "cm2_module", "twl6030_module", "mmchs_module"],
+ architectures = ["armv7"]
}
]
struct bfdriver* cur = NULL;
driverkit_list(&cur, &drivers);
for (size_t i=0; i<drivers; i++) {
- printf("%s:%s:%d: Found device driver class = %s\n", __FILE__, __FUNCTION__, __LINE__, cur->name);
+ //printf("%s:%s:%d: Found device driver class = %s\n", __FILE__, __FUNCTION__, __LINE__, cur->name);
cur += 1;
}
+ /*for (size_t i=0; i<argc; i++) {
+ printf("%s:%s:%d: argv[i] = %s\n", __FILE__, __FUNCTION__, __LINE__, argv[i]);
+ }*/
iref_t kaluga_iref = 0;
errval_t err = nameservice_blocking_lookup("ddomain_controller", &kaluga_iref);
assert(err_is_ok(err));
- err = ddomain_communication_init(kaluga_iref, 0x1);
+ err = ddomain_communication_init(kaluga_iref, atoi(argv[2]));
assert(err_is_ok(err));
- printf("%s:%s:%d: done initializing\n", __FILE__, __FUNCTION__, __LINE__);
- messages_handler_loop();
+ while(1) {
+ err = event_dispatch(get_default_waitset());
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "error in event_dispatch for messages_wait_and_handle_next hack");
+ }
+ }
+
return 0;
}
--- /dev/null
+--------------------------------------------------------------------------
+-- Copyright (c) 2007-2013, ETH Zurich.
+-- All rights reserved.
+--
+-- This file is distributed under the terms in the attached LICENSE file.
+-- If you do not find this file, copies can be found by writing to:
+-- ETH Zurich D-INFK, Universitaetstr. 6, CH-8092 Zurich. Attn: Systems Group.
+--
+-- Hakefile for omap44xx sd-card driver
+--
+--------------------------------------------------------------------------
+
+[
+ build library { target = "cm2_module",
+ cFiles = [
+ "cm2.c", "module.c", "service.c"
+ ],
+ mackerelDevices = [
+ "omap/omap44xx_l3init_cm2"
+ ],
+ flounderDefs = [ "cm2" ],
+ flounderBindings = [ "cm2" ],
+ architectures = ["armv7"]
+ }
+]
#include <barrelfish/barrelfish.h>
#include <driverkit/driverkit.h>
-#include <arch/arm/omap44xx/device_registers.h>
+#include "cm2.h"
-#include "mmchs.h"
-#include "cap_slots.h"
-
-void cm2_enable_hsmmc1(struct mmchs_driver_state* st)
+void cm2_enable_hsmmc1(struct cm2_driver_state* st)
{
omap44xx_l3init_cm2_cm_l3init_clkstctrl_clktrctrl_wrf(&st->l3init_cm2, 0x2);
omap44xx_l3init_cm2_cm_l3init_hsmmc1_clkctrl_modulemode_wrf(&st->l3init_cm2, 0x2);
while (omap44xx_l3init_cm2_cm_l3init_hsmmc1_clkctrl_idlest_rdf(&st->l3init_cm2) != 0x0);
}
-void cm2_enable_i2c(struct mmchs_driver_state* st, size_t i2c_index)
+void cm2_enable_i2c(struct cm2_driver_state* st, size_t i2c_index)
{
assert (i2c_index < 4);
!= 0x0);
}
-void cm2_init(struct mmchs_driver_state* st)
+void cm2_init(struct cm2_driver_state* st)
{
lvaddr_t l3init_vaddr;
- errval_t err = map_device_cap(st->caps[CM2_SLOT], &l3init_vaddr);
+ errval_t err = map_device_cap(st->cap, &l3init_vaddr);
assert(err_is_ok(err));
omap44xx_l3init_cm2_initialize(&st->l3init_cm2, (mackerel_addr_t)l3init_vaddr);
omap44xx_l4per_cm2_initialize(&st->l4per_cm2, (mackerel_addr_t)l3init_vaddr);
-
- lvaddr_t clkgen_vaddr;
- err = map_device_cap(st->caps[CLKGEN_CM2_SLOT], &clkgen_vaddr);
- assert(err_is_ok(err));
- omap44xx_ckgen_cm2_initialize(&st->clkgen_cm2, (mackerel_addr_t)clkgen_vaddr);
}
-int cm2_get_hsmmc1_base_clock(struct mmchs_driver_state* st)
+int cm2_get_hsmmc1_base_clock(struct cm2_driver_state* st)
{
return omap44xx_l3init_cm2_cm_l3init_hsmmc1_clkctrl_clksel_rdf(&st->l3init_cm2) == 0x0 ?
64000000 : 96000000;
--- /dev/null
+/*
+ * Copyright (c) 2012, ETH Zurich.
+ * All rights reserved.
+ *
+ * This file is distributed under the terms in the attached LICENSE file.
+ * If you do not find this file, copies can be found by writing to:
+ * ETH Zurich D-INFK, CAB F.78, Universitaetstr 6, CH-8092 Zurich.
+ */
+
+#ifndef __OMAP44XX_CM2_H__
+#define __OMAP44XX_CM2_H__
+
+#include <barrelfish/barrelfish.h>
+#include <dev/omap/omap44xx_l3init_cm2_dev.h>
+#include <dev/omap/omap44xx_l4per_cm2_dev.h>
+
+
+//#define CM2_DEBUG_ENABLE 1
+
+#if defined(CM2_DEBUG_ENABLE) || defined(GLOBAL_DEBUG)
+#define CM2_DEBUG(x...) printf(x)
+#else
+#define CM2_DEBUG(x...) ((void)0)
+#endif
+
+struct cm2_driver_state {
+ size_t level;
+ struct capref cap;
+ omap44xx_l3init_cm2_t l3init_cm2;
+ omap44xx_l4per_cm2_t l4per_cm2;
+};
+
+/* cm2.c */
+void cm2_enable_i2c(struct cm2_driver_state* st, size_t i2c_index);
+int cm2_get_hsmmc1_base_clock(struct cm2_driver_state* st);
+void cm2_enable_hsmmc1(struct cm2_driver_state*);
+void cm2_init(struct cm2_driver_state*);
+
+/* service.c */
+void cm2_init_service(struct cm2_driver_state* st, iref_t* iref);
+
+#endif /* __OMAP44XX_CM2_H__ */
--- /dev/null
+/**
+ * \file
+ * \brief MMCHS Driver main routine.
+ */
+/*
+ * Copyright (c) 2013, ETH Zurich.
+ * All rights reserved.
+ *
+ * This file is distributed under the terms in the attached LICENSE file.
+ * If you do not find this file, copies can be found by writing to:
+ * ETH Zurich D-INFK, Haldeneggsteig 4, CH-8092 Zurich. Attn: Systems Group.
+ */
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include <assert.h>
+
+#include <barrelfish/barrelfish.h>
+#include <driverkit/driverkit.h>
+
+#include "cm2.h"
+
+/**
+ * Driver initialization function. This function is called by the driver domain
+ * (see also 'create_handler' in ddomain_service.c).
+ * Typically through a request from the device manager.
+ *
+ * The init function is supposed to set `dev` to the exported service iref.
+ * The init function may use `bfi->dstate` to store additional state about the device.
+ *
+ * \param[in] bfi The instance of this driver.
+ * \param[in] name The name of this driver instance.
+ * \param[in] flags Additional flags (The exact flags supported is device/driver specific).
+ * \param[in] c Capabilities (for registers etc.) as provided by the device manager.
+ * The exact layout of the `c` is device specific.
+ * \param[out] dev The service iref over which the device can be contacted.
+ *
+ * \retval SYS_ERR_OK Device initialized successfully.
+ * \retval LIB_ERR_MALLOC_FAIL Unable to allocate memory for the driver.
+ */
+static errval_t init(struct bfdriver_instance* bfi, const char* name, uint64_t flags,
+ struct capref* caps, size_t caps_len, char** args, size_t args_len, iref_t* dev) {
+ CM2_DEBUG("%s:%s:%d: %s\n", __FILE__, __FUNCTION__, __LINE__, bfi->driver->name);
+
+ bfi->dstate = malloc(sizeof(struct cm2_driver_state));
+ if (bfi->dstate == NULL) {
+ return LIB_ERR_MALLOC_FAIL;
+ }
+
+ assert(bfi->dstate != NULL);
+
+ struct cm2_driver_state* st = (struct cm2_driver_state*) bfi->dstate;
+ st->cap = caps[0];
+
+ cm2_init(st);
+ cm2_init_service(st, dev);
+
+ return SYS_ERR_OK;
+}
+
+/**
+ * Instructs driver to attach to the device.
+ * This function is only called if the driver has previously detached
+ * from the device (see also detach).
+ *
+ * \note After detachment the driver can not assume anything about the
+ * configuration of the device.
+ *
+ * \param[in] bfi The instance of this driver.
+ * \retval SYS_ERR_OK Device initialized successfully.
+ */
+static errval_t attach(struct bfdriver_instance* bfi) {
+ CM2_DEBUG("%s:%s:%d: %s\n", __FILE__, __FUNCTION__, __LINE__, bfi->driver->name);
+
+ return SYS_ERR_OK;
+}
+
+/**
+ * Instructs driver to detach from the device.
+ * The driver must yield any control over to the device after this function returns.
+ * The device may be left in any state.
+ *
+ * \param[in] bfi The instance of this driver.
+ * \retval SYS_ERR_OK Device initialized successfully.
+ */
+static errval_t detach(struct bfdriver_instance* bfi) {
+ CM2_DEBUG("%s:%s:%d: %s\n", __FILE__, __FUNCTION__, __LINE__, bfi->driver->name);
+
+ return SYS_ERR_OK;
+}
+
+/**
+ * Instructs the driver to go in a particular sleep state.
+ * Supported states are platform/device specific.
+ *
+ * \param[in] bfi The instance of this driver.
+ * \retval SYS_ERR_OK Device initialized successfully.
+ */
+static errval_t set_sleep_level(struct bfdriver_instance* bfi, uint32_t level) {
+ CM2_DEBUG("%s:%s:%d: %s\n", __FILE__, __FUNCTION__, __LINE__, bfi->driver->name);
+
+ struct cm2_driver_state* uds = bfi->dstate;
+ uds->level = level;
+
+ return SYS_ERR_OK;
+}
+
+/**
+ * Destroys this driver instance. The driver will yield any
+ * control over the device and free any state allocated.
+ *
+ * \param[in] bfi The instance of this driver.
+ * \retval SYS_ERR_OK Device initialized successfully.
+ */
+static errval_t destroy(struct bfdriver_instance* bfi) {
+ CM2_DEBUG("%s:%s:%d: %s\n", __FILE__, __FUNCTION__, __LINE__, bfi->driver->name);
+ struct cm2_driver_state* uds = bfi->dstate;
+ free(uds);
+ bfi->dstate = NULL;
+
+ // XXX: Tear-down the service
+ bfi->device = 0x0;
+
+ return SYS_ERR_OK;
+}
+
+/**
+ * Registers the driver module with the system.
+ */
+DEFINE_MODULE(cm2, init, attach, detach, set_sleep_level, destroy);
--- /dev/null
+/**
+ * \file
+ * \brief Implementation of ata_rw28.if interface (to enable working vfs_fat)
+ */
+/*
+ * Copyright (c) 2013, ETH Zurich.
+ * All rights reserved.
+ *
+ * This file is distributed under the terms in the attached LICENSE file.
+ * If you do not find this file, copies can be found by writing to:
+ * ETH Zurich D-INFK, Haldeneggsteig 4, CH-8092 Zurich. Attn: Systems Group.
+ */
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include <assert.h>
+
+#include "cm2.h"
+
+#include <barrelfish/barrelfish.h>
+#include <barrelfish/nameservice_client.h>
+#include <if/cm2_defs.h>
+
+static errval_t cm2_enable_i2c_handler(struct cm2_binding *sv, uint32_t index)
+{
+ struct cm2_driver_state* ds = sv->st;
+ cm2_enable_i2c(ds, index);
+ return SYS_ERR_OK;
+}
+
+static errval_t cm2_get_hsmmc1_base_clock_handler(struct cm2_binding *sv, uint32_t* clock)
+{
+ struct cm2_driver_state* ds = sv->st;
+ *clock = cm2_get_hsmmc1_base_clock(ds);
+ return SYS_ERR_OK;
+}
+
+static errval_t cm2_enable_hsmmc1_handler(struct cm2_binding *sv)
+{
+ struct cm2_driver_state* ds = sv->st;
+ cm2_enable_hsmmc1(ds);
+ return SYS_ERR_OK;
+}
+
+static struct export_state {
+ struct cm2_binding* b;
+ bool is_done;
+ errval_t err;
+ iref_t iref;
+} service_export;
+
+static void export_cb(void *st, errval_t err, iref_t iref)
+{
+ service_export.is_done = true;
+ service_export.err = err;
+ service_export.iref = iref;
+
+ if (err_is_ok(err)) {
+ CM2_DEBUG("Exported ddomain service with iref: %"PRIu32"\n", iref);
+ err = nameservice_register("cm2", iref);
+ assert(err_is_ok(err));
+ }
+}
+static const struct cm2_rpc_rx_vtbl rx_vtbl = {
+ .enable_i2c_call = cm2_enable_i2c_handler,
+ .get_hsmmc1_base_clock_call = cm2_get_hsmmc1_base_clock_handler,
+ .enable_hsmmc1_call = cm2_enable_hsmmc1_handler
+};
+
+static errval_t client_connect(void *st, struct cm2_binding *b)
+{
+ service_export.b = b;
+ b->rpc_rx_vtbl = rx_vtbl;
+ b->st = st;
+ return SYS_ERR_OK;
+}
+
+void cm2_init_service(struct cm2_driver_state* st, iref_t* iref)
+{
+ errval_t err;
+ CM2_DEBUG("%s:%d: Starting server\n", __FUNCTION__, __LINE__);
+ err = cm2_export(st, export_cb, client_connect, get_default_waitset(), IDC_EXPORT_FLAGS_DEFAULT);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "call failed.");
+ }
+
+ while(!service_export.is_done) {
+ messages_wait_and_handle_next();
+ }
+
+ *iref = service_export.iref;
+ CM2_DEBUG("Service cm2 exported.\n");
+}
"omap/omap44xx_device_prm" ],
architectures = ["armv7"]
}
-
- -- build application {
- -- target = "fdif",
- -- cFiles = [ "fdif_domain.c"],
- -- addModules = ["fdif_module"],
- -- addLinkFlags = ["-T" ++ Config.source_dir ++ "/lib/driverkit/bfdrivers.ld" ]
- -- }
]
read_result(st);
omap44xx_fdif_fdif_ctrl_pr(st->printbuf, PRINT_BUFFER_SIZE, &st->devfdif);
- printf("%s\n", st->printbuf);
+ FDIF_DEBUG("%s\n", st->printbuf);
omap44xx_cam_cm2_pr(st->printbuf, PRINT_BUFFER_SIZE, &st->devclk);
- printf("%s\n", st->printbuf);
+ FDIF_DEBUG("%s\n", st->printbuf);
omap44xx_cam_prm_pr(st->printbuf, PRINT_BUFFER_SIZE, &st->dev);
- printf("%s\n", st->printbuf);
+ FDIF_DEBUG("%s\n", st->printbuf);
omap44xx_fdif_fdif_irqstatus_finish_irq_wrf(&st->devfdif, 2, 1);
while (omap44xx_fdif_fdif_sysconfig_softreset_rdf(&st->devfdif) != 0);
omap44xx_fdif_fdif_sysconfig_pr(st->printbuf, PRINT_BUFFER_SIZE, &st->devfdif);
- printf("%s\n", st->printbuf);
+ FDIF_DEBUG("%s\n", st->printbuf);
omap44xx_fdif_fdif_sysconfig_idlemode_wrf(&st->devfdif, 0x2);
omap44xx_fdif_fdif_sysconfig_standbymode_wrf(&st->devfdif, 0x2);
omap44xx_fdif_fdif_sysconfig_pr(st->printbuf, PRINT_BUFFER_SIZE, &st->devfdif);
- printf("%s\n", st->printbuf);
+ FDIF_DEBUG("%s\n", st->printbuf);
omap44xx_fdif_fdif_ctrl_max_tags_wrf(&st->devfdif, 0xA);
struct gimage {
uint32_t width;
uint32_t height;
- uint32_t bytes_per_pixel; /* 2:RGB16, 3:RGB, 4:RGBA */
+ uint32_t bytes_per_pixel; /* 2:RGB16, 3:RGB, 4:RGBA */
uint8_t pixel_data[320 * 240];
};
-#define FDIF_DEBUG(x...) printf("fdif: " x)
+//#define FDIF_DEBUG_ON 1
-#endif // FDIF_H_
\ No newline at end of file
+#if defined(FDIF_DEBUG_ON) || defined(GLOBAL_DEBUG)
+#define FDIF_DEBUG(x...) debug_printf(x)
+#else
+#define FDIF_DEBUG(x...) ((void)0)
+#endif
+
+
+#endif // FDIF_H_
+++ /dev/null
-#include <stdlib.h>
-#include <stdio.h>
-#include <string.h>
-#include <assert.h>
-
-#include <barrelfish/barrelfish.h>
-#include <driverkit/driverkit.h>
-#include <barrelfish/nameservice_client.h>
-
-/// XXX: TODO not needed once kaluga <-> driver domain communicate over dcontrol iface
-static errval_t find_cap_for(lpaddr_t address, size_t size, struct capref* out)
-{
- errval_t err;
- struct cnoderef argcn_cnref = {
- .croot = CPTR_ROOTCN,
- .cnode = ROOTCN_SLOT_ADDR(ROOTCN_SLOT_ARGCN),
- .level = CNODE_TYPE_OTHER,
- };
-
- struct capref device_cap_iter = {
- .cnode = argcn_cnref,
- .slot = 0
- };
-
- for (; device_cap_iter.slot < L2_CNODE_SLOTS; device_cap_iter.slot++) {
- // Get cap data
- struct capability cap;
- err = debug_cap_identify(device_cap_iter, &cap);
- // If cap type was Null, kernel returns error
- if (err_no(err) == SYS_ERR_IDENTIFY_LOOKUP ||
- err_no(err) == SYS_ERR_CAP_NOT_FOUND ||
- err_no(err) == SYS_ERR_LMP_CAPTRANSFER_SRC_LOOKUP) {
- continue;
- }
-
- struct frame_identity fid;
- err = frame_identify(device_cap_iter, &fid);
- if (err_is_fail(err)) {
- DEBUG_ERR(err, "Failure in frame_identify");
- return err;
- }
- assert(err_is_ok(err));
-
- lpaddr_t address_base = address & ~(BASE_PAGE_SIZE-1);
- // XXX: should be address+size <= ...
- // Need to add proper register size
- if (address_base >= fid.base &&
- (address_base + size) <= (fid.base + fid.bytes)) {
- *out = device_cap_iter;
- return SYS_ERR_OK;
- }
- }
-
- return DRIVERKIT_ERR_NO_CAP_FOUND;
-}
-
-
-int main(int argc, char** argv)
-{
- size_t drivers = 0;
- struct bfdriver* cur = NULL;
- driverkit_list(&cur, &drivers);
- for (size_t i=0; i<drivers; i++) {
- printf("%s:%s:%d: Found device driver class = %s\n", __FILE__, __FUNCTION__, __LINE__, cur->name);
- cur += 1;
- }
-
- struct capref* caps = calloc(1, sizeof(struct capref));
- errval_t err = find_cap_for(0x4A10A000, 4096, &caps[0]);
- if (err_is_fail(err)) {
- USER_PANIC_ERR(err, "finding cap failed.");
- }
- iref_t dev, ctrl;
- driverkit_create_driver("fdif", "fdif_inst", caps, 1, NULL, 0, 0, &dev, &ctrl);
-
- messages_handler_loop();
- return 0;
-}
[
build library { target = "mmchs_module",
cFiles = [
- "main.c", "cm2.c", "ctrlmod.c",
- "i2c.c", "mmchs.c", "twl6030.c",
- "service.c"
+ "main.c", "ctrlmod.c",
+ "mmchs.c", "service.c"
],
mackerelDevices = [
- "ti_i2c",
- "ti_twl6030",
"omap/omap44xx_mmchs1",
- "omap/omap44xx_sysctrl_padconf_core",
- "omap/omap44xx_l3init_cm2",
- "omap/omap44xx_ckgen_cm2",
- "omap/omap44xx_l4per_cm2"
+ "omap/omap44xx_sysctrl_padconf_core"
],
- flounderDefs = [ "ata_rw28" ],
+ flounderDefs = [ "ata_rw28", "cm2", "twl6030" ],
flounderBindings = [ "ata_rw28" ],
flounderTHCStubs = [ "ata_rw28" ],
architectures = ["armv7"]
}
- --build application {
- -- target = "mmchs",
- -- cFiles = [ "mmchs_domain.c"],
- -- addModules = ["mmchs_module"],
- -- addLinkFlags = ["-T" ++ Config.source_dir ++ "/lib/driverkit/bfdrivers.ld" ],
- -- mackerelDevices = [
- -- "ti_i2c",
- -- "ti_twl6030",
- -- "omap/omap44xx_mmchs1",
- -- "omap/omap44xx_sysctrl_padconf_core",
- -- "omap/omap44xx_l3init_cm2",
- -- "omap/omap44xx_ckgen_cm2",
- -- "omap/omap44xx_l4per_cm2"
- -- ]
- --}
]
#ifndef __CAP_SLOTS__
#define __CAP_SLOTS__
-#define CM2_SLOT 0
-#define CLKGEN_CM2_SLOT 1
-#define IC2_SLOT 2
-#define L4_PER_HSMMC1_SLOT 3
-#define PADCONF_CORE_SLOT 4
+#define PADCONF_CORE_SLOT 0
+#define L4_PER_HSMMC1_SLOT 1
#endif // __CAP_SLOTS__
#include <driverkit/driverkit.h>
-#include "twl6030.h"
#include "omap44xx_ctrlmod.h"
#include "mmchs.h"
// Step 3: Program desired SDMMC1_VDDS for MMC I/O in I2C attached power
// controller (3.0V)
- errval_t err = ti_twl6030_set_vmmc_vsel(st->twl, 3000);
+ errval_t err = st->twl6030_binding->rpc_tx_vtbl.vmmc_vsel(st->twl6030_binding, 3000);
assert(err_is_ok(err));
// Step 4: Set VMODE bit according to Step 3 (0x1 == 3.0V)
#include <assert.h>
#include <barrelfish/barrelfish.h>
+#include <barrelfish/nameservice_client.h>
#include <driverkit/driverkit.h>
#include "mmchs.h"
+
+static void cm2_connected(void *st, errval_t err, struct cm2_binding *b) {
+ MMCHS_DEBUG("Connected to cm2 driver\n");
+ assert(err_is_ok(err));
+ struct mmchs_driver_state* dst = (struct mmchs_driver_state*) st;
+ cm2_rpc_client_init(b);
+ dst->cm2_binding = b;
+}
+
+static void twl6030_connected(void *st, errval_t err, struct twl6030_binding *b) {
+ MMCHS_DEBUG("Connected to twl6030 driver\n");
+ assert(err_is_ok(err));
+ struct mmchs_driver_state* dst = (struct mmchs_driver_state*) st;
+ twl6030_rpc_client_init(b);
+ dst->twl6030_binding = b;
+}
+
+
/**
* Driver initialization function. This function is called by the driver domain
* (see also 'create_handler' in ddomain_service.c).
struct mmchs_driver_state* st = (struct mmchs_driver_state*) bfi->dstate;
st->caps = caps;
+ // Connect to the cm2 driver
+ iref_t cm2_iref;
+ errval_t err = nameservice_lookup("cm2", &cm2_iref);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "finding cm2 service failed.");
+ }
+ err = cm2_bind(cm2_iref, cm2_connected, st, get_default_waitset(), IDC_EXPORT_FLAG_NO_NOTIFY);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "call failed.");
+ }
+ while(st->cm2_binding == NULL) {
+ messages_wait_and_handle_next();
+ }
+ assert(st->cm2_binding != NULL);
+
+ // Connect to the twl6030 driver
+ iref_t twl6030_iref;
+ err = nameservice_lookup("twl6030", &twl6030_iref);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "finding cm2 service failed.");
+ }
+ err = twl6030_bind(twl6030_iref, twl6030_connected, st, get_default_waitset(), IDC_EXPORT_FLAG_NO_NOTIFY);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "call failed.");
+ }
+ while(st->twl6030_binding == NULL) {
+ messages_wait_and_handle_next();
+ }
+ assert(st->twl6030_binding != NULL);
+
// 1. Initialize the device:
- cm2_init(st);
- ti_twl6030_init(st);
ctrlmod_init(st);
- cm2_enable_hsmmc1(st);
+ err = st->cm2_binding->rpc_tx_vtbl.enable_hsmmc1(st->cm2_binding);
+ assert(err_is_ok(err));
sdmmc1_enable_power(st);
mmchs_init(st);
// 2. Export service to talk to the device:
- init_service(st);
-
- // 3. Set iref of your exported service (this is reported back to Kaluga)
- *dev = 0x00;
+ // FYI: Making this use THC+thread currently fails somewhere in the THC runtime
+ mmchs_init_service(st, dev);
return SYS_ERR_OK;
}
#include <driverkit/driverkit.h>
#include <arch/arm/omap44xx/device_registers.h>
+#include <if/cm2_defs.h>
#include "mmchs.h"
#include "cap_slots.h"
omap44xx_mmchs1_mmchs_sysctl_cen_wrf(&st->mmchs, 0x0);
omap44xx_mmchs1_mmchs_sysctl_ice_wrf(&st->mmchs, 0x1);
- MMCHS_DEBUG("%s:%d: clksel = %u\n", __FUNCTION__, __LINE__, cm2_get_hsmmc1_base_clock(st));
+ uint32_t clock = 0;
+ st->cm2_binding->rpc_tx_vtbl.get_hsmmc1_base_clock(st->cm2_binding, &clock);
+ MMCHS_DEBUG("%s:%d: clksel = %u\n", __FUNCTION__, __LINE__, clock);
change_clock_frequency_to_fit_protocol(st, 0x258);
MMCHS_DEBUG("%s:%d: Wait until internal clock is stable.\n", __FUNCTION__, __LINE__);
#include <barrelfish/barrelfish.h>
#include <dev/omap/omap44xx_mmchs1_dev.h>
-#include <dev/omap/omap44xx_l3init_cm2_dev.h>
-#include <dev/omap/omap44xx_ckgen_cm2_dev.h>
-#include <dev/omap/omap44xx_l4per_cm2_dev.h>
+
+#include <if/twl6030_defs.h>
+#include <if/cm2_defs.h>
#include "mmchs_debug.h"
-#include "omap44xx_cm2.h"
#include "omap44xx_ctrlmod.h"
-#include "i2c.h"
-#include "twl6030.h"
#define DBUF_SIZE (10*4096)
struct mmchs_driver_state {
uint64_t level;
+ iref_t iref;
- omap44xx_l3init_cm2_t l3init_cm2;
- omap44xx_l4per_cm2_t l4per_cm2;
- omap44xx_ckgen_cm2_t clkgen_cm2;
omap44xx_sysctrl_padconf_core_t ctrlmod;
omap44xx_mmchs1_t mmchs;
- ti_twl6030_t twl;
-
- struct capref* caps;
+ struct cm2_binding* cm2_binding;
+ struct twl6030_binding* twl6030_binding;
+ struct capref* caps;
char dbuf[DBUF_SIZE];
};
errval_t mmchs_read_block(struct mmchs_driver_state*, size_t block_nr, void *buffer);
errval_t mmchs_write_block(struct mmchs_driver_state*, size_t block_nr, void *buffer);
-void init_service(struct mmchs_driver_state*);
+void mmchs_init_service(struct mmchs_driver_state*, iref_t* iref);
#endif // MMCHS2_H
#ifndef MMCHS2_DEBUG_H
#define MMCHS2_DEBUG_H
-#define MMCHS_SERVICE_DEBUG 1
+//#define MMCHS_SERVICE_DEBUG 1
#if defined(MMCHS_SERVICE_DEBUG) || defined(GLOBAL_DEBUG)
#define MMCHS_DEBUG(x...) debug_printf(x)
+++ /dev/null
-#include <stdlib.h>
-#include <stdio.h>
-#include <string.h>
-#include <assert.h>
-
-#include <barrelfish/barrelfish.h>
-#include <driverkit/driverkit.h>
-#include <barrelfish/nameservice_client.h>
-
-#include "i2c.h"
-#include "twl6030.h"
-#include <arch/arm/omap44xx/device_registers.h>
-#include <maps/omap44xx_map.h>
-
-#include "cap_slots.h"
-
-/// XXX: TODO not needed once kaluga <-> driver domain communicate over dcontrol iface
-static errval_t find_cap_for(lpaddr_t address, size_t size, struct capref* out)
-{
- errval_t err;
- struct cnoderef argcn_cnref = {
- .croot = CPTR_ROOTCN,
- .cnode = ROOTCN_SLOT_ADDR(ROOTCN_SLOT_ARGCN),
- .level = CNODE_TYPE_OTHER,
- };
-
- struct capref device_cap_iter = {
- .cnode = argcn_cnref,
- .slot = 0
- };
-
- for (; device_cap_iter.slot < L2_CNODE_SLOTS; device_cap_iter.slot++) {
- // Get cap data
- struct capability cap;
- err = debug_cap_identify(device_cap_iter, &cap);
- // If cap type was Null, kernel returns error
- if (err_no(err) == SYS_ERR_IDENTIFY_LOOKUP ||
- err_no(err) == SYS_ERR_CAP_NOT_FOUND ||
- err_no(err) == SYS_ERR_LMP_CAPTRANSFER_SRC_LOOKUP) {
- continue;
- }
-
- struct frame_identity fid;
- err = frame_identify(device_cap_iter, &fid);
- if (err_is_fail(err)) {
- DEBUG_ERR(err, "Failure in frame_identify");
- return err;
- }
- assert(err_is_ok(err));
-
- lpaddr_t address_base = address & ~(BASE_PAGE_SIZE-1);
- // XXX: should be address+size <= ...
- // Need to add proper register size
- if (address_base >= fid.base &&
- (address_base + size) <= (fid.base + fid.bytes)) {
- *out = device_cap_iter;
- return SYS_ERR_OK;
- }
- }
-
- return DRIVERKIT_ERR_NO_CAP_FOUND;
-}
-
-
-int main(int argc, char** argv)
-{
- size_t drivers = 0;
- struct bfdriver* cur = NULL;
- driverkit_list(&cur, &drivers);
- for (size_t i=0; i<drivers; i++) {
- printf("%s:%s:%d: Found device driver class = %s\n", __FILE__, __FUNCTION__, __LINE__, cur->name);
- cur += 1;
- }
-
- struct capref* caps = calloc(5, sizeof(struct capref));
-
-
- errval_t err = find_cap_for(OMAP44XX_CM2, 0x1000, &caps[CM2_SLOT]);
- if (err_is_fail(err)) {
- USER_PANIC_ERR(err, "finding cap failed.");
- }
- err = find_cap_for(OMAP44XX_CLKGEN_CM2, 0x1000, &caps[CLKGEN_CM2_SLOT]);
- if (err_is_fail(err)) {
- USER_PANIC_ERR(err, "finding cap failed.");
- }
- err = find_cap_for(i2c_get_pbase(I2C_HC), 0x1000, &caps[IC2_SLOT]);
- if (err_is_fail(err)) {
- USER_PANIC_ERR(err, "finding cap failed.");
- }
-#define SYSCTRL_PADCONF_CORE 0x4a100000u
- err = find_cap_for(SYSCTRL_PADCONF_CORE, 0x1000, &caps[PADCONF_CORE_SLOT]);
- if (err_is_fail(err)) {
- USER_PANIC_ERR(err, "finding cap failed.");
- }
- err = find_cap_for(OMAP44XX_MAP_L4_PER_HSMMC1, OMAP44XX_MAP_L4_PER_HSMMC1_SIZE, &caps[L4_PER_HSMMC1_SLOT]);
- if (err_is_fail(err)) {
- USER_PANIC_ERR(err, "finding cap failed.");
- }
-
- iref_t dev, ctrl;
- driverkit_create_driver("mmchs", "mmchs_inst", caps, 1, NULL, 0, 0, &dev, &ctrl);
-
- messages_handler_loop();
- return 0;
-}
+++ /dev/null
-/*
- * Copyright (c) 2012, ETH Zurich.
- * All rights reserved.
- *
- * This file is distributed under the terms in the attached LICENSE file.
- * If you do not find this file, copies can be found by writing to:
- * ETH Zurich D-INFK, CAB F.78, Universitaetstr 6, CH-8092 Zurich.
- */
-
-#ifndef __OMAP44XX_CM2_H__
-#define __OMAP44XX_CM2_H__
-
-#include <barrelfish/barrelfish.h>
-#include <dev/omap/omap44xx_l3init_cm2_dev.h>
-#include <dev/omap/omap44xx_ckgen_cm2_dev.h>
-#include <dev/omap/omap44xx_l4per_cm2_dev.h>
-
-struct mmchs_driver_state;
-
-void cm2_enable_i2c(struct mmchs_driver_state* st, size_t i2c_index);
-int cm2_get_hsmmc1_base_clock(struct mmchs_driver_state* st);
-void cm2_enable_hsmmc1(struct mmchs_driver_state*);
-void cm2_init(struct mmchs_driver_state*);
-
-#endif /* __OMAP44XX_CM2_H__ */
#include <barrelfish/nameservice_client.h>
#include <if/ata_rw28_defs.h>
-#include <if/ata_rw28_thc.h>
#include <thc/thc.h>
#include "mmchs.h"
#define SECTION_SIZE 512
#define SECTION_ROUND_UP(x) ( ((x) + (SECTION_SIZE-1)) & (~(SECTION_SIZE-1)) )
-static void read_dma(struct mmchs_driver_state* st, struct ata_rw28_thc_service_binding_t *sv,
+static void read_dma(struct ata_rw28_binding *sv,
uint32_t read_size, uint32_t start_lba)
{
+ struct mmchs_driver_state* st = (struct mmchs_driver_state*)sv->st;
+
size_t buffer_size = SECTION_ROUND_UP(read_size);
MMCHS_DEBUG("%s:%d read_size=%d buffer_size=%d\n", __FUNCTION__, __LINE__, read_size, buffer_size);
void *buffer = malloc(buffer_size);
assert(err_is_ok(err));
bufptr += SECTION_SIZE;
}
- sv->send.read_dma(sv, buffer, buffer_size);
- free(buffer);
+
+ errval_t err = ata_rw28_read_dma_response__tx(sv, MKCLOSURE(free, buffer), buffer, buffer_size);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "call failed.");
+ }
}
-static void read_dma_block(struct mmchs_driver_state* st, struct ata_rw28_thc_service_binding_t *sv, uint32_t lba)
+static void read_dma_block(struct ata_rw28_binding *sv, uint32_t lba)
{
MMCHS_DEBUG("%s:%d lba=%d\n", __FUNCTION__, __LINE__, lba);
+ struct mmchs_driver_state* st = (struct mmchs_driver_state*)sv->st;
+
void *buffer = malloc(SECTION_SIZE);
assert(buffer != NULL);
errval_t err = mmchs_read_block(st, lba, buffer);
assert(err_is_ok(err));
- sv->send.read_dma_block(sv, buffer, SECTION_SIZE);
- free(buffer);
+ err = ata_rw28_read_dma_block_response__tx(sv, MKCLOSURE(free, buffer), buffer, SECTION_SIZE);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "call failed.");
+ }
}
-static void write_dma(struct mmchs_driver_state* st, struct ata_rw28_thc_service_binding_t *sv,
- uint8_t *buffer, size_t buffer_len, uint32_t lba)
+/*static void write_dma(struct ata_rw28_binding *sv,
+ uint8_t *buffer, size_t buffer_size, uint32_t lba)
{
MMCHS_DEBUG("%s:%d\n", __FUNCTION__, __LINE__);
- sv->send.write_dma(sv, LIB_ERR_NOT_IMPLEMENTED);
-}
+ errval_t err = ata_rw28_write_dma_response__tx(sv, MKCLOSURE(free, buffer), LIB_ERR_NOT_IMPLEMENTED);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "call failed.");
+ }
+}*/
-static void identify_device(struct mmchs_driver_state* st, struct ata_rw28_thc_service_binding_t *sv)
+static void identify_device(struct ata_rw28_binding *sv)
{
MMCHS_DEBUG("%s:%d\n", __FUNCTION__, __LINE__);
- sv->send.identify_device(sv, NULL, 0);
+ errval_t err = ata_rw28_identify_device_response__tx(sv, NOP_CONT, NULL, 0);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "call failed.");
+ }
}
-
-static void flush_cache(struct mmchs_driver_state* st, struct ata_rw28_thc_service_binding_t *sv)
+static void flush_cache(struct ata_rw28_binding *sv)
{
MMCHS_DEBUG("%s:%d\n", __FUNCTION__, __LINE__);
- sv->send.flush_cache(sv, SYS_ERR_OK);
+ errval_t err = ata_rw28_flush_cache_response__tx(sv, NOP_CONT, SYS_ERR_OK);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "call failed.");
+ }
}
-static void service_client(struct mmchs_driver_state* st, struct ata_rw28_thc_service_binding_t *sv)
+static struct export_state {
+ struct ata_rw28_binding* b;
+ bool is_done;
+ errval_t err;
+ iref_t iref;
+} service_export;
+
+static void export_cb(void *st, errval_t err, iref_t iref)
+{
+ service_export.is_done = true;
+ service_export.err = err;
+ service_export.iref = iref;
+
+ if (err_is_ok(err)) {
+ MMCHS_DEBUG("Exported ddomain service with iref: %"PRIu32"\n", iref);
+ err = nameservice_register("mmchs", iref);
+ assert(err_is_ok(err));
+ }
+}
+static const struct ata_rw28_rx_vtbl rx_vtbl = {
+ .read_dma_call = read_dma,
+ .read_dma_block_call = read_dma_block,
+ //.write_dma_call = write_dma,
+ .identify_device_call = identify_device,
+ .flush_cache_call = flush_cache,
+};
+
+static errval_t client_connect(void *st, struct ata_rw28_binding *b)
{
- DO_FINISH({
- bool stop = false;
- while (!stop) {
- ata_rw28_service_msg_t m;
- sv->recv_any(sv, &m, (struct ata_rw28_service_selector) {
- .read_dma = 1,
- .read_dma_block = 1,
- .write_dma = 1,
- .identify_device = 1,
- .flush_cache = 1
- });
-
- switch (m.msg) {
-
- case ata_rw28_read_dma:
- read_dma(st, sv, m.args.read_dma.in.read_size, m.args.read_dma.in.start_lba);
- break;
-
- case ata_rw28_read_dma_block:
- read_dma_block(st, sv, m.args.read_dma_block.in.lba);
- break;
-
- case ata_rw28_write_dma:
- write_dma(st, sv, m.args.write_dma.in.buffer, m.args.write_dma.in.buffer_size, m.args.write_dma.in.lba);
- break;
-
- case ata_rw28_identify_device:
- identify_device(st, sv);
- break;
-
- case ata_rw28_flush_cache:
- flush_cache(st, sv);
- break;
-
- default:
- assert(!"Unexpected message");
- break;
- }
- }
- });
+ service_export.b = b;
+ b->st = st;
+ return SYS_ERR_OK;
}
-void init_service(struct mmchs_driver_state* st)
+
+void mmchs_init_service(struct mmchs_driver_state* st, iref_t* iref)
{
errval_t err;
- iref_t iref;
- struct ata_rw28_thc_service_binding_t *sv;
- struct ata_rw28_binding *b;
- struct ata_rw28_thc_export_info info;
-
MMCHS_DEBUG("%s:%d: Starting server\n", __FUNCTION__, __LINE__);
- err = ata_rw28_thc_export(&info,
- "mmchs",
- get_default_waitset(),
- IDC_EXPORT_FLAGS_DEFAULT,
- &iref);
-
- MMCHS_DEBUG("%s:%d: Done export iref=%"PRIuIREF"\n", __FUNCTION__, __LINE__, iref);
+ err = ata_rw28_export(st, export_cb, client_connect, get_default_waitset(), IDC_EXPORT_FLAGS_DEFAULT);
if (err_is_fail(err)) {
- DEBUG_ERR(err, "export failed");
- abort();
+ USER_PANIC_ERR(err, "call failed.");
}
- DO_FINISH({
- while (1) {
- MMCHS_DEBUG("%s:%d: Server waiting for connection\n", __FUNCTION__, __LINE__);
- err = ata_rw28_thc_accept(&info, &b);
- if (err_is_fail(err)) {
- DEBUG_ERR(err, "accept failed");
- abort();
- }
-
- sv = malloc(sizeof(struct ata_rw28_thc_service_binding_t));
- if (sv == NULL) {
- DEBUG_ERR(err, "malloc failed");
- abort();
- }
-
- err = ata_rw28_thc_init_service(sv, b, b);
- if (err_is_fail(err)) {
- DEBUG_ERR(err, "init failed");
- abort();
- }
-
- MMCHS_DEBUG("%s:%d: Got service %p\n", __FUNCTION__, __LINE__, sv);
- ASYNC({service_client(st, sv);});
- }
- });
+ while(!service_export.is_done) {
+ messages_wait_and_handle_next();
+ }
+ *iref = service_export.iref;
+ MMCHS_DEBUG("Service mmchs exported.\n");
}
architectures = ["armv7"]
}
-
- --build application {
- -- target = "sdma",
- -- cFiles = [ "sdma_domain.c"],
- -- addModules = ["sdma_module"],
- -- addLinkFlags = ["-T" ++ Config.source_dir ++ "/lib/driverkit/bfdrivers.ld" ]
- --}
]
omap_sdma_init(bfi->dstate, (mackerel_addr_t)dev_base, sdma_irq_handler);
// 2. Export service to talk to the device:
- start_service(bfi->dstate);
-
- // 3. Set iref of your exported service (this is reported back to Kaluga)
- *dev = 0x00;
+ sdma_init_service(bfi->dstate, dev);
return SYS_ERR_OK;
}
#include <if/omap_sdma_defs.h>
#include <bitmacros.h>
+//#define SDMA_DEBUG_ON 1
+
+#if defined(SDMA_DEBUG_ON) || defined(MMCHS_SERVICE_DEBUG) || defined(GLOBAL_DEBUG)
+#define SDMA_DEBUG(x...) printf(x)
+#else
+#define SDMA_DEBUG(x...) ((void)0)
+#endif
+
struct sdma_driver_state;
-void start_service(struct sdma_driver_state* st);
+void sdma_init_service(struct sdma_driver_state* st, iref_t* iref);
errval_t mem_copy(struct sdma_driver_state* st, struct capref dst_cap, struct capref src_cap);
errval_t mem_fill(struct sdma_driver_state* st, struct capref dst_cap, uint8_t color);
+++ /dev/null
-#include <stdlib.h>
-#include <stdio.h>
-#include <string.h>
-#include <assert.h>
-
-#include <barrelfish/barrelfish.h>
-#include <driverkit/driverkit.h>
-#include <barrelfish/nameservice_client.h>
-
-#include <arch/arm/omap44xx/device_registers.h>
-#include <maps/omap44xx_map.h>
-
-/// XXX: TODO not needed once kaluga <-> driver domain communicate over dcontrol iface
-static errval_t find_cap_for(lpaddr_t address, size_t size, struct capref* out)
-{
- errval_t err;
- struct cnoderef argcn_cnref = {
- .croot = CPTR_ROOTCN,
- .cnode = ROOTCN_SLOT_ADDR(ROOTCN_SLOT_ARGCN),
- .level = CNODE_TYPE_OTHER,
- };
-
- struct capref device_cap_iter = {
- .cnode = argcn_cnref,
- .slot = 0
- };
-
- for (; device_cap_iter.slot < L2_CNODE_SLOTS; device_cap_iter.slot++) {
- // Get cap data
- struct capability cap;
- err = debug_cap_identify(device_cap_iter, &cap);
- // If cap type was Null, kernel returns error
- if (err_no(err) == SYS_ERR_IDENTIFY_LOOKUP ||
- err_no(err) == SYS_ERR_CAP_NOT_FOUND ||
- err_no(err) == SYS_ERR_LMP_CAPTRANSFER_SRC_LOOKUP) {
- continue;
- }
-
- struct frame_identity fid;
- err = frame_identify(device_cap_iter, &fid);
- if (err_is_fail(err)) {
- DEBUG_ERR(err, "Failure in frame_identify");
- return err;
- }
- assert(err_is_ok(err));
-
- lpaddr_t address_base = address & ~(BASE_PAGE_SIZE-1);
- // XXX: should be address+size <= ...
- // Need to add proper register size
- if (address_base >= fid.base &&
- (address_base + size) <= (fid.base + fid.bytes)) {
- *out = device_cap_iter;
- return SYS_ERR_OK;
- }
- }
-
- return DRIVERKIT_ERR_NO_CAP_FOUND;
-}
-
-
-int main(int argc, char** argv)
-{
- size_t drivers = 0;
- struct bfdriver* cur = NULL;
- driverkit_list(&cur, &drivers);
- for (size_t i=0; i<drivers; i++) {
- printf("%s:%s:%d: Found device driver class = %s\n", __FILE__, __FUNCTION__, __LINE__, cur->name);
- cur += 1;
- }
-
- struct capref* caps = calloc(1, sizeof(struct capref));
- errval_t err = find_cap_for(OMAP44XX_MAP_L4_CFG_SDMA, OMAP44XX_MAP_L4_CFG_SDMA_SIZE, &caps[0]);
- if (err_is_fail(err)) {
- USER_PANIC_ERR(err, "finding cap failed.");
- }
-
- iref_t dev, ctrl;
- driverkit_create_driver("sdma", "sdma_inst", caps, 1, NULL, 0, 0, &dev, &ctrl);
-
- messages_handler_loop();
- return 0;
-}
+/**
+ * \file
+ * \brief Implementation of ata_rw28.if interface (to enable working vfs_fat)
+ */
/*
- * Copyright (c) 2014, ETH Zurich.
+ * Copyright (c) 2013, ETH Zurich.
* All rights reserved.
*
* This file is distributed under the terms in the attached LICENSE file.
* If you do not find this file, copies can be found by writing to:
- * ETH Zurich D-INFK, CAB F.78, Universitaetstr 6, CH-8092 Zurich.
+ * ETH Zurich D-INFK, Haldeneggsteig 4, CH-8092 Zurich. Attn: Systems Group.
*/
#include <stdlib.h>
#include <barrelfish/barrelfish.h>
#include <barrelfish/nameservice_client.h>
-
#include <if/omap_sdma_defs.h>
-#include <if/omap_sdma_thc.h>
-#include <thc/thc.h>
#include "sdma.h"
-static void run_service(struct sdma_driver_state* st, struct omap_sdma_thc_service_binding_t *sv)
-{
- omap_sdma_service_msg_t msg;
- bool loop = true;
-
- // this is the bitmap of messages we are interested in receiving
- struct omap_sdma_service_selector selector = {
- .mem_copy = 1, .mem_copy_2d = 1,
- .mem_fill = 1, .mem_fill_2d = 1,
- };
-
- while (loop) {
- // receive any message
- sv->recv_any(sv, &msg, selector);
+static errval_t mem_copy_handler(struct omap_sdma_binding *sv, struct capref dst, struct capref src, errval_t* err) {
+ struct sdma_driver_state* ds = sv->st;
+ *err = mem_copy(ds, dst, src);
+ return SYS_ERR_OK;
+}
- errval_t reterr = SYS_ERR_OK;
+static errval_t mem_fill_handler(struct omap_sdma_binding *sv, struct capref dst, uint8_t color, errval_t* err) {
+ struct sdma_driver_state* ds = sv->st;
+ *err = mem_fill(ds, dst, color);
+ return SYS_ERR_OK;
+}
- // dispatch it
- switch(msg.msg) {
- case omap_sdma_mem_copy:
- reterr = mem_copy(st,
- msg.args.mem_copy.in.dst,
- msg.args.mem_copy.in.src);
- sv->send.mem_copy(sv, reterr);
- break;
- case omap_sdma_mem_fill:
- reterr = mem_fill(st,
- msg.args.mem_fill.in.dst,
- msg.args.mem_fill.in.color);
- sv->send.mem_fill(sv, reterr);
- break;
- case omap_sdma_mem_copy_2d:
- reterr = mem_copy_2d(st,
- msg.args.mem_copy_2d.in.dst,
- msg.args.mem_copy_2d.in.src,
- msg.args.mem_copy_2d.in.count,
- msg.args.mem_copy_2d.in.transparent,
- msg.args.mem_copy_2d.in.color);
- sv->send.mem_copy_2d(sv, reterr);
- break;
- case omap_sdma_mem_fill_2d:
- reterr = mem_fill_2d(st,
- msg.args.mem_fill_2d.in.dst,
- msg.args.mem_fill_2d.in.count,
- msg.args.mem_fill_2d.in.color);
- sv->send.mem_fill_2d(sv, reterr);
- break;
- default:
- debug_printf("unexpected message: %d\n", msg.msg);
- loop = false;
- break;
- }
- }
+static errval_t mem_copy_2d_handler(struct omap_sdma_binding *sv,
+ omap_sdma_addr_2d_t dst, omap_sdma_addr_2d_t src, omap_sdma_count_2d_t count,
+ bool transparent, uint32_t color, errval_t* err) {
+ struct sdma_driver_state* ds = sv->st;
+ *err = mem_copy_2d(ds, dst, src, count, transparent, color);
+ return SYS_ERR_OK;
+}
- free(sv);
+static errval_t mem_fill_2d_handler(struct omap_sdma_binding *sv,
+ omap_sdma_addr_2d_t dst, uint32_t color, omap_sdma_count_2d_t count,
+ errval_t* err) {
+ struct sdma_driver_state* ds = sv->st;
+ *err = mem_fill_2d(ds, dst, count, color);
+ return SYS_ERR_OK;
}
-void start_service(struct sdma_driver_state* st)
-{
+static struct export_state {
+ struct omap_sdma_binding* b;
+ bool is_done;
errval_t err;
-
- struct omap_sdma_thc_export_info e_info;
- struct omap_sdma_thc_service_binding_t *sv;
- struct omap_sdma_binding *b;
iref_t iref;
+} service_export;
- err = omap_sdma_thc_export(&e_info, "sdma",
- get_default_waitset(),
- IDC_EXPORT_FLAGS_DEFAULT,
- &iref);
- if (err_is_fail(err)) {
- USER_PANIC_ERR(err, "thc export failed");
+static void export_cb(void *st, errval_t err, iref_t iref)
+{
+ service_export.is_done = true;
+ service_export.err = err;
+ service_export.iref = iref;
+
+ if (err_is_ok(err)) {
+ SDMA_DEBUG("Exported ddomain service with iref: %"PRIu32"\n", iref);
+ err = nameservice_register("sdma", iref);
+ assert(err_is_ok(err));
}
+}
- DO_FINISH({
- while(true) {
- err = omap_sdma_thc_accept(&e_info, &b);
- if (err_is_fail(err)) {
- USER_PANIC_ERR(err, "thc accept failed");
- }
+static const struct omap_sdma_rpc_rx_vtbl rx_vtbl = {
+ .mem_copy_call = mem_copy_handler,
+ .mem_fill_call = mem_fill_handler,
+ .mem_copy_2d_call = mem_copy_2d_handler,
+ .mem_fill_2d_call = mem_fill_2d_handler,
+};
- sv = malloc(sizeof(struct omap_sdma_thc_service_binding_t));
- assert(sv != NULL);
+static errval_t client_connect(void *st, struct omap_sdma_binding *b)
+{
+ service_export.b = b;
+ b->rpc_rx_vtbl = rx_vtbl;
+ b->st = st;
+ return SYS_ERR_OK;
+}
- err = omap_sdma_thc_init_service(sv, b, b);
- if (err_is_fail(err)) {
- USER_PANIC_ERR(err, "thc init failed");
- }
+void sdma_init_service(struct sdma_driver_state* st, iref_t* iref)
+{
+ errval_t err;
+ SDMA_DEBUG("%s:%d: Starting server\n", __FUNCTION__, __LINE__);
+ err = omap_sdma_export(st, export_cb, client_connect, get_default_waitset(), IDC_EXPORT_FLAGS_DEFAULT);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "call failed.");
+ }
- ASYNC({run_service(st, sv);});
- }
- });
+ while(!service_export.is_done) {
+ messages_wait_and_handle_next();
+ }
+ *iref = service_export.iref;
+ SDMA_DEBUG("Service sdma exported.\n");
}
--- /dev/null
+--------------------------------------------------------------------------
+-- Copyright (c) 2007-2013, ETH Zurich.
+-- All rights reserved.
+--
+-- This file is distributed under the terms in the attached LICENSE file.
+-- If you do not find this file, copies can be found by writing to:
+-- ETH Zurich D-INFK, Universitaetstr. 6, CH-8092 Zurich. Attn: Systems Group.
+--
+-- Hakefile for omap44xx sd-card driver
+--
+--------------------------------------------------------------------------
+
+[
+ build library {
+ target = "twl6030_module",
+ cFiles = [ "i2c.c", "twl6030.c", "module.c", "service.c" ],
+ mackerelDevices = [
+ "ti_i2c",
+ "ti_twl6030"
+ ],
+ flounderDefs = [ "twl6030", "cm2" ],
+ flounderBindings = [ "twl6030" ],
+ architectures = ["armv7"]
+ }
+]
#include <barrelfish/barrelfish.h>
#include <driverkit/driverkit.h>
+#include <assert.h>
#include <dev/ti_i2c_dev.h>
-#include "omap44xx_cm2.h" // for turning on I2C clocks
#include "i2c.h"
#include "twl6030.h"
-#include "mmchs.h"
-#include "cap_slots.h"
#if defined(I2C_SERVICE_DEBUG) || defined(MMCHS_SERVICE_DEBUG) || defined(GLOBAL_DEBUG)
#define I2C_DEBUG(x...) debug_printf(x)
/*
* \brief initialize I2C controller `i`.
*/
-void ti_i2c_init(struct mmchs_driver_state* st, int i)
+void ti_i2c_init(struct twl6030_driver_state* st, int i)
{
I2C_DEBUG("%s:%d\n", __FUNCTION__, __LINE__);
// map & initialize mackerel device
lvaddr_t i2c_vbase;
- errval_t err = map_device_cap(st->caps[IC2_SLOT], &i2c_vbase);
+ errval_t err = map_device_cap(st->cap, &i2c_vbase);
assert(err_is_ok(err));
ti_i2c_initialize(&i2c[i], (mackerel_addr_t)i2c_vbase);
ti_i2c_t *dev = &i2c[i];
// turn on clocks
- cm2_enable_i2c(st, i);
-
+ assert(st->cm2_binding != NULL);
+ assert(st->cm2_binding->rpc_tx_vtbl.enable_i2c != NULL);
+ err = st->cm2_binding->rpc_tx_vtbl.enable_i2c(st->cm2_binding, i);
+ assert(err_is_ok(err));
I2C_DEBUG("%s:%d\n", __FUNCTION__, __LINE__);
// TODO?: enable interrupts
//ti_i2c_sysc_pr(prbuf, PBS-1, dev);
//I2C_DEBUG("%s\n", prbuf);
-
-
return;
}
uint8_t *buf;
};
-struct mmchs_driver_state;
-void ti_i2c_init(struct mmchs_driver_state* st, int i);
+struct twl6030_driver_state;
+void ti_i2c_init(struct twl6030_driver_state* st, int i);
errval_t ti_i2c_transfer(int i, struct i2c_msg *msgs, size_t msgcount);
lpaddr_t i2c_get_pbase(size_t dev);
--- /dev/null
+/**
+ * \file
+ * \brief MMCHS Driver main routine.
+ */
+/*
+ * Copyright (c) 2013, ETH Zurich.
+ * All rights reserved.
+ *
+ * This file is distributed under the terms in the attached LICENSE file.
+ * If you do not find this file, copies can be found by writing to:
+ * ETH Zurich D-INFK, Haldeneggsteig 4, CH-8092 Zurich. Attn: Systems Group.
+ */
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include <assert.h>
+
+#include <barrelfish/barrelfish.h>
+#include <barrelfish/nameservice_client.h>
+#include <driverkit/driverkit.h>
+
+#include <if/cm2_defs.h>
+
+#include "twl6030.h"
+
+static void cm2_connected(void *st, errval_t err, struct cm2_binding *b) {
+ TWL_DEBUG("Connected to cm2 driver\n");
+ assert(err_is_ok(err));
+ struct twl6030_driver_state* dst = (struct twl6030_driver_state*) st;
+ dst->cm2_binding = b;
+ cm2_rpc_client_init(b);
+}
+
+/**
+ * Driver initialization function. This function is called by the driver domain
+ * (see also 'create_handler' in ddomain_service.c).
+ * Typically through a request from the device manager.
+ *
+ * The init function is supposed to set `dev` to the exported service iref.
+ * The init function may use `bfi->dstate` to store additional state about the device.
+ *
+ * \param[in] bfi The instance of this driver.
+ * \param[in] name The name of this driver instance.
+ * \param[in] flags Additional flags (The exact flags supported is device/driver specific).
+ * \param[in] c Capabilities (for registers etc.) as provided by the device manager.
+ * The exact layout of the `c` is device specific.
+ * \param[out] dev The service iref over which the device can be contacted.
+ *
+ * \retval SYS_ERR_OK Device initialized successfully.
+ * \retval LIB_ERR_MALLOC_FAIL Unable to allocate memory for the driver.
+ */
+static errval_t init(struct bfdriver_instance* bfi, const char* name, uint64_t flags,
+ struct capref* caps, size_t caps_len, char** args, size_t args_len, iref_t* dev) {
+ TWL_DEBUG("%s:%s:%d: %s\n", __FILE__, __FUNCTION__, __LINE__, bfi->driver->name);
+
+ bfi->dstate = malloc(sizeof(struct twl6030_driver_state));
+ if (bfi->dstate == NULL) {
+ return LIB_ERR_MALLOC_FAIL;
+ }
+
+ assert(bfi->dstate != NULL);
+
+ struct twl6030_driver_state* st = (struct twl6030_driver_state*) bfi->dstate;
+ st->cap = caps[0];
+
+ // Connect to the cm2 driver
+ iref_t cm2_iref;
+ errval_t err = nameservice_lookup("cm2", &cm2_iref);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "finding cm2 service failed.");
+ }
+
+ err = cm2_bind(cm2_iref, cm2_connected, st, get_default_waitset(), IDC_EXPORT_FLAG_NO_NOTIFY);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "call failed.");
+ }
+
+ while(st->cm2_binding == NULL) {
+ messages_wait_and_handle_next();
+ }
+ assert(st->cm2_binding != NULL);
+
+
+ ti_twl6030_init(st);
+ twl6030_init_service(st, dev);
+
+ return SYS_ERR_OK;
+}
+
+/**
+ * Instructs driver to attach to the device.
+ * This function is only called if the driver has previously detached
+ * from the device (see also detach).
+ *
+ * \note After detachment the driver can not assume anything about the
+ * configuration of the device.
+ *
+ * \param[in] bfi The instance of this driver.
+ * \retval SYS_ERR_OK Device initialized successfully.
+ */
+static errval_t attach(struct bfdriver_instance* bfi) {
+ TWL_DEBUG("%s:%s:%d: %s\n", __FILE__, __FUNCTION__, __LINE__, bfi->driver->name);
+
+ return SYS_ERR_OK;
+}
+
+/**
+ * Instructs driver to detach from the device.
+ * The driver must yield any control over to the device after this function returns.
+ * The device may be left in any state.
+ *
+ * \param[in] bfi The instance of this driver.
+ * \retval SYS_ERR_OK Device initialized successfully.
+ */
+static errval_t detach(struct bfdriver_instance* bfi) {
+ TWL_DEBUG("%s:%s:%d: %s\n", __FILE__, __FUNCTION__, __LINE__, bfi->driver->name);
+
+ return SYS_ERR_OK;
+}
+
+/**
+ * Instructs the driver to go in a particular sleep state.
+ * Supported states are platform/device specific.
+ *
+ * \param[in] bfi The instance of this driver.
+ * \retval SYS_ERR_OK Device initialized successfully.
+ */
+static errval_t set_sleep_level(struct bfdriver_instance* bfi, uint32_t level) {
+ TWL_DEBUG("%s:%s:%d: %s\n", __FILE__, __FUNCTION__, __LINE__, bfi->driver->name);
+
+ struct twl6030_driver_state* uds = bfi->dstate;
+ uds->level = level;
+
+ return SYS_ERR_OK;
+}
+
+/**
+ * Destroys this driver instance. The driver will yield any
+ * control over the device and free any state allocated.
+ *
+ * \param[in] bfi The instance of this driver.
+ * \retval SYS_ERR_OK Device initialized successfully.
+ */
+static errval_t destroy(struct bfdriver_instance* bfi) {
+ TWL_DEBUG("%s:%s:%d: %s\n", __FILE__, __FUNCTION__, __LINE__, bfi->driver->name);
+ struct twl6030_driver_state* uds = bfi->dstate;
+ free(uds);
+ bfi->dstate = NULL;
+
+ // XXX: Tear-down the service
+ bfi->device = 0x0;
+
+ return SYS_ERR_OK;
+}
+
+/**
+ * Registers the driver module with the system.
+ *
+ * To link this particular module in your driver domain,
+ * add it to the addModules list in the Hakefile.
+ */
+DEFINE_MODULE(twl6030, init, attach, detach, set_sleep_level, destroy);
--- /dev/null
+/**
+ * \file
+ * \brief Implementation of ata_rw28.if interface (to enable working vfs_fat)
+ */
+/*
+ * Copyright (c) 2013, ETH Zurich.
+ * All rights reserved.
+ *
+ * This file is distributed under the terms in the attached LICENSE file.
+ * If you do not find this file, copies can be found by writing to:
+ * ETH Zurich D-INFK, Haldeneggsteig 4, CH-8092 Zurich. Attn: Systems Group.
+ */
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include <assert.h>
+
+#include "twl6030.h"
+
+#include <barrelfish/barrelfish.h>
+#include <barrelfish/nameservice_client.h>
+#include <if/twl6030_defs.h>
+
+
+
+static errval_t vmmc_csel_off(struct twl6030_binding *sv)
+{
+ struct twl6030_driver_state* ds = sv->st;
+ ti_twl6030_vmmc_off(ds->twl);
+ return SYS_ERR_OK;
+}
+
+static errval_t vmmc_on_handler(struct twl6030_binding *sv)
+{
+ struct twl6030_driver_state* ds = sv->st;
+ ti_twl6030_vmmc_on(ds->twl);
+ return SYS_ERR_OK;
+}
+
+static errval_t vmmc_vsel_handler(struct twl6030_binding *sv, uint32_t vsel)
+{
+ struct twl6030_driver_state* ds = sv->st;
+ return ti_twl6030_set_vmmc_vsel(ds->twl, vsel);
+}
+
+static struct export_state {
+ struct twl6030_binding* b;
+ bool is_done;
+ errval_t err;
+ iref_t iref;
+} service_export;
+
+static void export_cb(void *st, errval_t err, iref_t iref)
+{
+ service_export.is_done = true;
+ service_export.err = err;
+ service_export.iref = iref;
+
+ if (err_is_ok(err)) {
+ TWL_DEBUG("Exported ddomain service with iref: %"PRIu32"\n", iref);
+ err = nameservice_register("twl6030", iref);
+ assert(err_is_ok(err));
+ }
+}
+static const struct twl6030_rpc_rx_vtbl rx_vtbl = {
+ .vmmc_on_call = vmmc_on_handler,
+ .vmmc_off_call = vmmc_csel_off,
+ .vmmc_vsel_call = vmmc_vsel_handler,
+};
+
+static errval_t client_connect(void *st, struct twl6030_binding *b)
+{
+ service_export.b = b;
+ b->rpc_rx_vtbl = rx_vtbl;
+ b->st = st;
+ return SYS_ERR_OK;
+}
+
+void twl6030_init_service(struct twl6030_driver_state* st, iref_t* iref)
+{
+ errval_t err;
+ TWL_DEBUG("%s:%d: Starting server\n", __FUNCTION__, __LINE__);
+ err = twl6030_export(st, export_cb, client_connect, get_default_waitset(), IDC_EXPORT_FLAGS_DEFAULT);
+ if (err_is_fail(err)) {
+ USER_PANIC_ERR(err, "call failed.");
+ }
+
+ while(!service_export.is_done) {
+ messages_wait_and_handle_next();
+ }
+ *iref = service_export.iref;
+ TWL_DEBUG("Service twl6030 exported.\n");
+}
// I2C slave address for id1 reads and writes is 0x48
#define ID1_I2C_ADDR 0x48
-#include "mmchs_debug.h"
-#if defined(TWL_SERIVCE_DEBUG) || defined(MMCHS_SERVICE_DEBUG) || defined(GLOBAL_DEBUG)
-#define TWL_DEBUG(x...) printf(x)
-#else
-#define TWL_DEBUG(x...) ((void)0)
-#endif
inline uint8_t _ti_twl6030_id1_read_8(void *d, size_t off)
{
return;
}
-void ti_twl6030_init(struct mmchs_driver_state* st)
+void ti_twl6030_init(struct twl6030_driver_state* st)
{
TWL_DEBUG("%s:%d\n", __FUNCTION__, __LINE__);
ti_i2c_init(st, I2C_HC);
#ifndef __TI_TWL6030_H__
#define __TI_TWL6030_H__
-#include <barrelfish/types.h>
+#include <barrelfish/barrelfish.h>
#include <errors/errno.h>
+#include <if/cm2_defs.h>
// I2C Host controller id
#define I2C_HC 0
+//#define TWL_SERIVCE_DEBUG 1
+
+#if defined(TWL_SERIVCE_DEBUG) || defined(MMCHS_SERVICE_DEBUG) || defined(GLOBAL_DEBUG)
+#define TWL_DEBUG(x...) printf(x)
+#else
+#define TWL_DEBUG(x...) ((void)0)
+#endif
+
uint8_t _ti_twl6030_id1_read_8(void *d, size_t off);
void _ti_twl6030_id1_write_8(void *d, size_t off, uint8_t regval);
#define ti_twl6030_id1_read_8(dev, off) _ti_twl6030_id1_read_8(dev, off)
#define ti_twl6030_id1_write_8(dev, off, regval) _ti_twl6030_id1_write_8(dev, off, regval)
#include <dev/ti_twl6030_dev.h>
-struct mmchs_driver_state;
-void ti_twl6030_init(struct mmchs_driver_state*);
-errval_t ti_twl6030_set_vmmc_vsel(ti_twl6030_t twl, int millis);
+struct twl6030_driver_state {
+ size_t level;
+ struct capref cap;
+ ti_twl6030_t twl;
+ struct cm2_binding* cm2_binding;
+};
+void ti_twl6030_init(struct twl6030_driver_state*);
+errval_t ti_twl6030_set_vmmc_vsel(ti_twl6030_t twl, int millis);
void ti_twl6030_vmmc_pr(ti_twl6030_t twl);
-
void ti_twl6030_vmmc_on(ti_twl6030_t twl);
void ti_twl6030_vmmc_off(ti_twl6030_t twl);
+/* service.c */
+void twl6030_init_service(struct twl6030_driver_state* st, iref_t* iref);
+
+
#endif // __TI_TWL6030_H__
#include "kaluga.h"
+static void start_driverdomain(char* record) {
+ struct module_info* mi = find_module("driverdomain");
+ if (mi != NULL) {
+ errval_t err = mi->start_function(0, mi, record, NULL);
+ assert(err_is_ok(err));
+ }
+}
+
static errval_t omap44xx_startup(void)
{
errval_t err;
err = init_cap_manager();
assert(err_is_ok(err));
- struct module_info* mi = find_module("driverdomain");
- if (mi != NULL) {
- err = mi->start_function(0, mi, "hw.arm.omap44xx.fdif {}", NULL);
- assert(err_is_ok(err));
- }
- mi = find_module("sdma");
- if (mi != NULL) {
- err = mi->start_function(0, mi, "hw.arm.omap44xx.sdma {}", NULL);
- assert(err_is_ok(err));
- }
- mi = find_module("mmchs");
- if (mi != NULL) {
- err = mi->start_function(0, mi, "hw.arm.omap44xx.mmchs {}", NULL);
- assert(err_is_ok(err));
- }
- mi = find_module("prcm");
+ start_driverdomain("fdif {}");
+ start_driverdomain("sdma {}");
+ start_driverdomain("mmchs { dep1: 'cm2', dep2: 'twl6030' }");
+
+ struct module_info* mi = find_module("prcm");
if (mi != NULL) {
err = mi->start_function(0, mi, "hw.arm.omap44xx.prcm {}", NULL);
assert(err_is_ok(err));
}
+
mi = find_module("serial");
if (mi != NULL) {
err = mi->start_function(0, mi, "hw.arm.omap44xx.uart {}", NULL);
};
static struct allowed_registers fdif = {
- .binary = "hw.arm.omap44xx.fdif",
+ .binary = "fdif",
.registers =
{
{OMAP44XX_CAM_CM2, 0x1000},
}
};
-static struct allowed_registers mmchs = {
- .binary = "hw.arm.omap44xx.mmchs",
+static struct allowed_registers twl6030 = {
+ .binary = "twl6030",
.registers =
{
- {OMAP44XX_CM2, 0x1000},
- {OMAP44XX_CLKGEN_CM2, 0x1000},
- {OMAP44XX_L4PER_CM2, 0x1000},
- // i2c
{OMAP44XX_MAP_L4_PER_I2C1, OMAP44XX_MAP_L4_PER_I2C1_SIZE},
- {OMAP44XX_MAP_L4_PER_I2C2, OMAP44XX_MAP_L4_PER_I2C2_SIZE},
- {OMAP44XX_MAP_L4_PER_I2C3, OMAP44XX_MAP_L4_PER_I2C3_SIZE},
- {OMAP44XX_MAP_L4_PER_I2C4, OMAP44XX_MAP_L4_PER_I2C4_SIZE},
- // ctrlmodules
- {OMAP44XX_MAP_L4_CFG_SYSCTRL_GENERAL_CORE, OMAP44XX_MAP_L4_CFG_SYSCTRL_GENERAL_CORE_SIZE},
- {OMAP44XX_MAP_L4_WKUP_SYSCTRL_GENERAL_WKUP, OMAP44XX_MAP_L4_WKUP_SYSCTRL_GENERAL_WKUP_SIZE},
+ {0x0, 0x0}
+ }
+};
+
+static struct allowed_registers cm2 = {
+ .binary = "cm2",
+ .registers =
+ {
+ {OMAP44XX_CM2, 0x1000},
+ {0x0, 0x0}
+ }
+};
+
+
+static struct allowed_registers mmchs = {
+ .binary = "mmchs",
+ .registers =
+ {
{OMAP44XX_MAP_L4_CFG_SYSCTRL_PADCONF_CORE, OMAP44XX_MAP_L4_CFG_SYSCTRL_PADCONF_CORE_SIZE},
- {OMAP44XX_MAP_L4_WKUP_SYSCTRL_PADCONF_WKUP, OMAP44XX_MAP_L4_WKUP_SYSCTRL_PADCONF_WKUP_SIZE},
- // MMCHS
{OMAP44XX_MAP_L4_PER_HSMMC1, OMAP44XX_MAP_L4_PER_HSMMC1_SIZE},
- {OMAP44XX_MAP_L4_PER_HSMMC2, OMAP44XX_MAP_L4_PER_HSMMC2_SIZE},
- {OMAP44XX_MAP_L4_PER_MMC_SD3, OMAP44XX_MAP_L4_PER_MMC_SD3_SIZE},
- {OMAP44XX_MAP_L4_PER_MMC_SD4, OMAP44XX_MAP_L4_PER_MMC_SD4_SIZE},
- {OMAP44XX_MAP_L4_PER_MMC_SD5, OMAP44XX_MAP_L4_PER_MMC_SD5_SIZE},
{0x0, 0x0}
}
};
};
static struct allowed_registers sdma = {
- .binary = "hw.arm.omap44xx.sdma",
+ .binary = "sdma",
.registers =
{
{OMAP44XX_MAP_L4_CFG_SDMA, OMAP44XX_MAP_L4_CFG_SDMA_SIZE},
static struct allowed_registers* omap44xx[] = {
&usb,
&fdif,
+ &twl6030,
+ &cm2,
&mmchs,
&prcm,
&omap_uart,
return SYS_ERR_OK;
}
-
-/**
- * \brief Startup function for new-style ARMv7 drivers.
- *
- * Launches the driver instance in a driver domain instead.
- */
-errval_t
-newstyle_start_function(coreid_t where, struct module_info* driver, char* record,
- struct driver_argument* int_arg)
-{
- assert(driver != NULL);
- assert(record != NULL);
+static void provide_driver_with_caps(struct driver_instance* drv, char* name) {
errval_t err;
struct monitor_blocking_binding *m = get_monitor_blocking_binding();
}
- struct domain_instance* inst = instantiate_driver_domain(0);
- struct driver_instance* drv = ddomain_create_driver_instance("fdif", "fdif_panda");
-
- char* name;
- err = oct_read(record, "%s", &name);
- assert(err_is_ok(err));
- KALUGA_DEBUG("%s:%d: Starting driver for %s\n", __FUNCTION__, __LINE__, name);
+ KALUGA_DEBUG("%s:%d: Finding caps for driver for %s\n", __FUNCTION__, __LINE__, name);
for (size_t i=0; regs[i] != NULL; i++) {
if(strcmp(name, regs[i]->binary) != 0) {
continue;
assert(err_is_ok(err));
}
}
+}
+
+
+/**
+ * \brief Startup function for new-style ARMv7 drivers.
+ *
+ * Launches the driver instance in a driver domain instead.
+ */
+errval_t
+newstyle_start_function(coreid_t where, struct module_info* driver, char* record,
+ struct driver_argument* int_arg)
+{
+ assert(driver != NULL);
+ assert(record != NULL);
+ errval_t err;
+
+ struct domain_instance* inst = instantiate_driver_domain(where);
+
+ char* dep1;
+ err = oct_read(record, "_ { dep1: %s }", &dep1);
+ if (err_is_ok(err)) {
+ struct driver_instance* drv1 = ddomain_create_driver_instance(dep1, dep1);
+ provide_driver_with_caps(drv1, dep1);
+ free(dep1);
+ ddomain_instantiate_driver(inst, drv1);
+ }
+
+ char* dep2;
+ err = oct_read(record, "_ { dep2: %s }", &dep2);
+ if (err_is_ok(err)) {
+ struct driver_instance* drv2 = ddomain_create_driver_instance(dep2, dep2);
+ provide_driver_with_caps(drv2, dep2);
+ free(dep2);
+ ddomain_instantiate_driver(inst, drv2);
+ }
+
+ char* name;
+ err = oct_read(record, "%s", &name);
+ assert(err_is_ok(err));
+
+ struct driver_instance* drv = ddomain_create_driver_instance(name, name);
+ provide_driver_with_caps(drv, name);
free(name);
ddomain_instantiate_driver(inst, drv);
#ifndef KALUGA_DEBUG_H_
#define KALUGA_DEBUG_H_
+//#define KALUGA_DEBUG_ON
-#if defined(KALUGA_SERVICE_DEBUG) || defined(GLOBAL_DEBUG)
+#if defined(KALUGA_DEBUG_ON) || defined(GLOBAL_DEBUG)
#define KALUGA_DEBUG(x...) debug_printf(x)
#else
#define KALUGA_DEBUG(x...) ((void)0)
(*argv)[new_size] = NULL;
}
-static errval_t launch_driver_domain(coreid_t where, size_t did, struct module_info* ddomain)
+static errval_t launch_driver_domain(coreid_t where, uint64_t did, struct module_info* ddomain)
{
assert(ddomain != NULL);
errval_t err = SYS_ERR_OK;
char **argv = NULL;
int argc = ddomain->argc;
- argv = malloc((argc+1) * sizeof(char *)); // +1 for trailing NULL
+ argv = malloc(sizeof(char*)*ddomain->argc); // +1 for trailing NULL
assert(argv != NULL);
+
memcpy(argv, ddomain->argv, (argc+1) * sizeof(char *));
assert(argv[argc] == NULL);
- char* did_str = malloc(26);
+ char* did_str = calloc(26, sizeof(char));
assert(did_str != NULL);
- snprintf(did_str, 26, "%"PRIx64"", did);
+ snprintf(did_str, 26, "%"PRIu64"", did);
argv_push(&argc, &argv, did_str);
err = spawn_program_with_caps(where, ddomain->path, argv,
return err;
}
+static void wait_for_id(struct domain_instance* di) {
+ while (di->b == NULL) {
+ messages_wait_and_handle_next();
+ }
+ KALUGA_DEBUG("%s:%s:%d: done with waiting for ID\n", __FILE__, __FUNCTION__, __LINE__);
+}
+
struct domain_instance* instantiate_driver_domain(coreid_t where) {
static uint64_t did = 1;
USER_PANIC_ERR(err, "call failed.");
}
struct domain_instance* di = ddomain_create_domain_instance(did);
- did++;
+ wait_for_id(di);
+ did++;
return di;
}