On 05/08/2019 21:15, BALATON Zoltan wrote:
Signed-off-by: BALATON Zoltan
<balaton(a)eik.bme.hu>
---
drivers/pci.c | 51 +++++++++++++++++++++++++++++++++++++--------------
drivers/pci.fs | 41 +++++++++++++++++++++++++++++++++++++++++
drivers/vga.fs | 4 ++--
forth/device/other.fs | 6 ++++++
4 files changed, 86 insertions(+), 16 deletions(-)
This is on top of Mark's previous patches from the openbios mailing
list applied to openbios master:
9a32ed9 Implement missing words for the ATI FCode ROM to test ati-vga emulation
b90ac41 virtio: use instance value to initialise C instance parameter
ac467a3 lsi: use instance value to hold sd_private_t pointer
177684a pc_kbd: use instance value to initialise C instance parameter
d5fdb98 pc_serial: remove separate init word
7c20840 pci: call set-args before configuring PCI device nodes
f37460e pci: remove explicit setting of my-self from PCI devices
b548924 pci: remove explicit find-device from PCI devices
b1ca78f x86: set active package and current instance to root device node before probe
6222a47 SPARC64: set active package and current instance to root device node before
probe
5cd41e5 ppc: set active package and current instance to root device node before probe
e68504f ppc: move New World uninorth and nvram device node creation to the root device
86aa740 nvram: ensure that NVRAM configuration is separate from NVRAM node creation
e959bfd libopenbios: remove REGISTER_NAMED_NODE and REGISTER_NAMED_NODE_PHANDLE macros
abc4553 pci: remove ob_pci_initialize() and ob_pci_empty_node
0a63c74 pci: convert to use BIND_NODE_METHODS() macro
57ff6ea virtio: convert to use BIND_NODE_METHODS() macro
ea3a8eb lsi: convert to use BIND_NODE_METHODS() macro
32ff529 lsi: don't change active package when setting device alias
f63f5ee nvram: convert to use BIND_NODE_METHODS() macro
03c53be usbhid: convert to use BIND_NODE_METHODS() macro
365b2c1 pmu: convert to use BIND_NODE_METHODS() macro
60125f5 macio: convert to use BIND_NODE_METHODS() macro
7d23b31 cuda: convert to use BIND_NODE_METHODS() macro
305d629 escc: convert to use BIND_NODE_METHODS() macro
4a0aea1 adb: convert to use BIND_NODE_METHODS() macro
0081f71 ide: convert to use BIND_NODE_METHODS() macro
79a241c floppy: convert to use BIND_NODE_METHODS() macro
01ea2e4 pc_serial: convert to use BIND_NODE_METHODS() macro
9eb09a9 pc_kbd: convert to use BIND_NODE_METHODS() macro
8945ab4 libopenbios: introduce BIND_NODE_METHODS() macro
e9491ea admin/devices.fs: Format assigned-addresses propertyadmin/devices.fs: Format
assigned-addresses propertyadmin/devices.fs: Format assigned-addresses
propertyadmin/devices.fs: Format assigned-addresses propertyadmin/devices.fs: Format
assigned-addresses propertyadmin/devices.fs: Format assigned-addresses
propertyadmin/devices.fs: Format assigned-addresses propertyadmin/devices.fs: Format
assigned-addresses propertyadmin/devices.fs: Format assigned-addresses
propertyadmin/devices.fs: Format assigned-addresses propertyadmin/devices.fs: Format
assigned-addresses propertyadmin/devices.fs: Format assigned-addresses
propertyadmin/devices.fs: Format assigned-addresses propertyadmin/devices.fs: Format
assigned-addresses propertyadmin/devices.fs: Format assigned-addresses
propertyadmin/devices.fs: Format assigned-addresses property
c79e0ec (origin/master, origin/HEAD) SPARC64: use serial console when QEMU is launched
with -vga none
admin/devices.fs: Format assigned-addresses property is
https://mail.coreboot.org/hyperkitty/list/openbios@openbios.org/thread/WHL7…
and additionally to the above I also have another patch from Mark that
I can't find now in the list archives even though I remember I've replyed
to it and had a discussion about having 3 or 2 cases if-else statement.
diff --git a/drivers/pci.c b/drivers/pci.c
index 4bc02c9..eb5f7d3 100644
--- a/drivers/pci.c
+++ b/drivers/pci.c
@@ -408,20 +408,32 @@ static void ob_pci_unmap(ucell virt, ucell size) {
static void
ob_pci_bus_map_in(int *idx)
{
- uint32_t ba;
- ucell size;
- ucell virt;
-
- PCI_DPRINTF("ob_pci_bar_map_in idx=%p\n", idx);
+ fword("pci-map-in");
+}
- size = POP();
- POP();
- POP();
- ba = POP();
+static void
+ob_pci_bus_map_out(int *idx)
+{
+ /* Should call pci-map-out but nothing to do in it yet */
+ fword("2drop");
+}
- virt = ob_pci_map(ba, size);
+static void
+ob_pci_config_read8(int *idx)
+{
+ cell hi = POP();
Should this not be ucell?
+ pci_addr addr = PCI_ADDR(PCI_BUS(hi),
PCI_DEV(hi), PCI_FN(hi));
+ uint8_t val = pci_config_read8(addr, hi & 0xff);
+ PUSH(val);
+}
- PUSH(virt);
+static void
+ob_pci_config_write8(int *idx)
+{
+ cell hi = POP();
and here too?
+ pci_addr addr = PCI_ADDR(PCI_BUS(hi),
PCI_DEV(hi), PCI_FN(hi));
+ cell val = POP();
+ pci_config_write8(addr, hi & 0xff, val & 0xff);
}
What about the other config-* words? Given that you're done the byte implementation
then you might as well do the same for the other accesses.
static void
@@ -459,7 +471,10 @@ NODE_METHODS(ob_pci_bus_node) = {
{ "close", ob_pci_close },
{ "decode-unit", ob_pci_decode_unit },
{ "encode-unit", ob_pci_encode_unit },
- { "pci-map-in", ob_pci_bus_map_in },
+ { "map-in", ob_pci_bus_map_in },
+ { "map-out", ob_pci_bus_map_out },
+ { "config-b@", ob_pci_config_read8 },
+ { "config-b!", ob_pci_config_write8 },
{ "dma-alloc", ob_pci_dma_alloc },
{ "dma-free", ob_pci_dma_free },
{ "dma-map-in", ob_pci_dma_map_in },
@@ -473,7 +488,14 @@ static void
ob_pci_bridge_map_in(int *idx)
{
/* As per the IEEE-1275 PCI specification, chain up to the parent */
- call_parent_method("pci-map-in");
+ call_parent_method("map-in");
+}
+
+static void
+ob_pci_bridge_map_out(int *idx)
+{
+ /* As per the IEEE-1275 PCI specification, chain up to the parent */
+ call_parent_method("map-out");
}
NODE_METHODS(ob_pci_bridge_node) = {
@@ -481,7 +503,8 @@ NODE_METHODS(ob_pci_bridge_node) = {
{ "close", ob_pci_close },
{ "decode-unit", ob_pci_decode_unit },
{ "encode-unit", ob_pci_encode_unit },
- { "pci-map-in", ob_pci_bridge_map_in },
+ { "map-in", ob_pci_bridge_map_in },
+ { "map-out", ob_pci_bridge_map_out },
{ "dma-alloc", ob_pci_dma_alloc },
{ "dma-free", ob_pci_dma_free },
{ "dma-map-in", ob_pci_dma_map_in },
diff --git a/drivers/pci.fs b/drivers/pci.fs
index a7b56e1..327c9c9 100644
--- a/drivers/pci.fs
+++ b/drivers/pci.fs
@@ -37,4 +37,45 @@
then
;
+: pci-map-in ( addr.lo addr.mid addr.hi size -- virt )
+ \ Ignore everything but addr.hi and find assigned addr for BAR
+ drop nip nip
+ \ Save my-self and set it to same as active package because otherwise
+ \ decode-phys below seems to be confused. Maybe this should not be needed
+ my-self swap active-package ihandle>phandle to my-self
+ " assigned-addresses" active-package get-package-property 0= if
+ begin
+ decode-phys ( bar prop prop-len phys.lo phys.mid phys.hi )
+ dup 0fffffff and 6 pick 0fffffff and = if
+ 2drop -rot
+ decode-int drop decode-int drop 2drop
+ ( bar addr.lo )
+ \ Now translate addr.lo, This may be wrong
+ \ maybe we should look at parent's ranges instead?
+ over 18 rshift 3 and 1 = if
+ " reg" active-package parent get-package-property 0= if
+ ( bar addr.lo prop prop-len reg.addr reg.size )
+ decode-int -rot decode-int 3drop
+ +
+ then
+ then
+ nip swap to my-self
+ exit
+ else
+ 3drop \ no match, try next
+ then
+ \ Drop the size as we don't need it
+ decode-int drop decode-int drop
+ dup 0=
+ until
+ 3drop
+ to my-self
+ -1 \ not found
+ else
+ drop
+ to my-self
+ -1 \ could not find assigned-addresses
+ then
+ ;
+
[THEN]
A couple of comments here: using Forth here makes this the only PCI word that is
implemented in Forth rather than C which tends to make debugging a lot more
difficult. I'd much prefer to have the implementation in one place and then consider
a conversion later if required.
Secondly this doesn't seem to be correct in that it doesn't take the physical
address
and map it to a virtual address and so it assumes this area has been pre-mapped. Is
this another piece of code borrowed from SLOF, since it runs in real mode rather than
virtual mode?
diff --git a/drivers/vga.fs b/drivers/vga.fs
index 53dcff0..f3ffda7 100644
--- a/drivers/vga.fs
+++ b/drivers/vga.fs
@@ -146,14 +146,14 @@ defer vbe-iow!
: map-fb ( -- )
cfg-bar0 pci-bar>pci-addr if \ ( pci-addr.lo pci-addr.mid pci-addr.hi size )
- " pci-map-in" $call-parent
+ " map-in" $call-parent
to fb-addr
then
;
: map-mmio ( -- )
cfg-bar2 pci-bar>pci-addr if \ ( pci-addr.lo pci-addr.mid pci-addr.hi size )
- " pci-map-in" $call-parent
+ " map-in" $call-parent
to mmio-addr
then
;
diff --git a/forth/device/other.fs b/forth/device/other.fs
index 1bed9b8..0ff34b6 100644
--- a/forth/device/other.fs
+++ b/forth/device/other.fs
@@ -58,21 +58,27 @@ defer (poke)
\ 5.3.7.2 Device-register access
: rb@ ( addr -- byte )
+ ioc@
;
: rw@ ( waddr -- w )
+ iow@
;
: rl@ ( qaddr -- quad )
+ iol@
;
: rb! ( byte addr -- )
+ ioc!
;
: rw! ( w waddr -- )
+ iow!
;
: rl! ( quad qaddr -- )
+ iol!
;
: rx@ ( oaddr - o )
I've had a read of the specifications and it's not very clear what type of
addresses
these are supposed to take - are they PCI addresses or virtual addresses? Can you
tell from your ATI FCode ROM?
The other issue is that I'm not convinced that these words belong in this file, since
you're overriding the default implementations with ones that assume little-endian
access. I think the correct solution here is implement these words as part of the PCI
bus node and use set-token to override the FCode implementation as detailed in the
IEEE-1275 specification.
ATB,
Mark.