summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAleksa Vuckovic <aleksa@vuckovic.cc>2023-03-09 01:22:07 +0100
committerAleksa Vuckovic <aleksa@vuckovic.cc>2023-03-09 01:22:07 +0100
commiteb3b263b11e90902841dc21c5a55c45e59128542 (patch)
treeaa06c0e5f04907c4f92ec51b3b94f07e98ebd4ee
parent48a4f607403c074252d3e77b2e0b3c1a8f3b86c7 (diff)
pcie device enumeration
-rw-r--r--kernel/include/mcfg.h4
-rw-r--r--kernel/include/pci.h49
-rw-r--r--kernel/src/devices/pci.c96
-rw-r--r--kernel/src/main.c2
-rw-r--r--kernel/src/mem/pmm.c2
-rw-r--r--kernel/src/scheduler/ap_startup.c2
6 files changed, 146 insertions, 9 deletions
diff --git a/kernel/include/mcfg.h b/kernel/include/mcfg.h
index 9f062c0..2e238cf 100644
--- a/kernel/include/mcfg.h
+++ b/kernel/include/mcfg.h
@@ -6,8 +6,8 @@
struct config_space_mcfgt {
uint64_t base_addr;
uint16_t pci_seg_group;
- uint8_t start_pci_bus;
- uint8_t end_pci_bus;
+ uint8_t start_bus;
+ uint8_t end_bus;
uint32_t reserved;
} __attribute__((packed));
typedef struct config_space_mcfgt config_space_mcfgt;
diff --git a/kernel/include/pci.h b/kernel/include/pci.h
new file mode 100644
index 0000000..01d97fc
--- /dev/null
+++ b/kernel/include/pci.h
@@ -0,0 +1,49 @@
+#ifndef PCI_H
+#define PCI_H
+
+#include <types.h>
+
+struct pci_dev {
+ uint16_t vendor_id;
+ uint16_t device_id;
+ uint16_t command;
+ uint16_t status;
+ uint8_t revision_id;
+ uint8_t progif;
+ uint8_t subclass;
+ uint8_t class_;
+ uint8_t cache_line_size;
+ uint8_t latency_timer;
+ uint8_t header_type;
+ uint8_t bist;
+};
+typedef struct pci_dev pci_dev;
+
+const char *class_string[] = {
+ "Unclassified",
+ "Mass Storage Controller",
+ "Network Controller",
+ "Display Controller",
+ "Multimedia Controller",
+ "Memory Controller",
+ "Bridge",
+ "Simple Communication Controller",
+ "Base System Peripheral",
+ "Input Device Controller",
+ "Docking Station",
+ "Processor",
+ "Serial Bus Controller",
+ "Wireless Controller",
+ "Intelligent Controller",
+ "Satellite Communication Controller",
+ "Encryption Controller",
+ "Signal Processing Controller",
+ "Processing Accelerator",
+ "Non-Essential Instrumentation",
+};
+
+const char *subclass_string[] = {
+
+};
+
+#endif
diff --git a/kernel/src/devices/pci.c b/kernel/src/devices/pci.c
index af0308a..978e9e9 100644
--- a/kernel/src/devices/pci.c
+++ b/kernel/src/devices/pci.c
@@ -1,10 +1,100 @@
#include <types.h>
#include <rsdp.h>
#include <libk/stdio.h>
+#include <libk/serial_stdio.h>
#include <mcfg.h>
#include <heap.h>
#include <paging.h>
#include <libk/string.h>
+#include <pci.h>
+
+const char *vendor_name(uint64_t vendor_id)
+{
+ switch (vendor_id) {
+ case 0x8086:
+ return "Intel";
+ case 0x1022:
+ return "AMD";
+ default:
+ return "Unknown";
+ }
+}
+
+void enumerate_function(uint64_t dev_addr, uint64_t function)
+{
+ uint64_t func_addr = dev_addr + (function << 12);
+
+ map_addr(func_addr, func_addr, FLAG_PRESENT);
+ pci_dev *pci_func = (pci_dev *)kalloc(sizeof(pci_dev));
+ memcpy(pci_func, (uint64_t *)func_addr, sizeof(pci_dev));
+
+ if (pci_func->device_id == 0)
+ goto error;
+ if (pci_func->device_id == 0xFFFF)
+ goto error;
+
+ const char *vendor_str = vendor_name(pci_func->vendor_id);
+ size_t class_str =
+ pci_func->class_ < sizeof(class_string) ? pci_func->class_ : 0;
+
+ printf("%s, 0x%x, %s, 0x%x\n", vendor_str, pci_func->device_id,
+ class_string[class_str], pci_func->subclass);
+
+error:
+ kfree(pci_func);
+}
+
+void enumerate_device(uint64_t bus_addr, uint64_t device)
+{
+ uint64_t dev_addr = bus_addr + (device << 15);
+
+ map_addr(dev_addr, dev_addr, FLAG_PRESENT);
+ pci_dev *pci_device = (pci_dev *)kalloc(sizeof(pci_dev));
+ memcpy(pci_device, (uint64_t *)bus_addr, sizeof(pci_dev));
+
+ if (pci_device->device_id == 0)
+ goto error;
+ if (pci_device->device_id == 0xFFFF)
+ goto error;
+
+ size_t func;
+ for (func = 0; func < 8; func++) {
+ enumerate_function(dev_addr, func);
+ }
+
+error:
+ kfree(pci_device);
+}
+
+void enumerate_bus(uint64_t base_addr, uint64_t bus)
+{
+ uint64_t bus_addr = base_addr + (bus << 20);
+
+ map_addr(bus_addr, bus_addr, FLAG_PRESENT);
+ pci_dev *pci_device = (pci_dev *)kalloc(sizeof(pci_dev));
+ memcpy(pci_device, (uint64_t *)bus_addr, sizeof(pci_dev));
+
+ if (pci_device->device_id == 0)
+ goto error;
+ if (pci_device->device_id == 0xFFFF)
+ goto error;
+
+ size_t dev;
+ for (dev = 0; dev < 32; dev++) {
+ enumerate_device(bus_addr, dev);
+ }
+
+error:
+ kfree(pci_device);
+}
+
+void enumerate_cfg_space(config_space_mcfgt *cfg_space)
+{
+ size_t i;
+ for (i = cfg_space->start_bus; i < cfg_space->end_bus; i++) {
+ enumerate_bus(cfg_space->base_addr, i);
+ }
+}
void read_mcfgt()
{
@@ -31,9 +121,9 @@ void read_mcfgt()
for (i = 0; i < len; i++) {
memcpy(cfg_space, (uint64_t *)mcfgt_cfg_addr,
sizeof(config_space_mcfgt));
- printf("addr: 0x%x, group: %d, start: %d, stop: %d\n",
- cfg_space->base_addr, cfg_space->pci_seg_group,
- cfg_space->start_pci_bus, cfg_space->end_pci_bus);
+ /* printf("addr: 0x%x, group: %d, start: %d, stop: %d\n", cfg_space->base_addr, cfg_space->pci_seg_group, cfg_space->start_bus, cfg_space->end_bus); */
+ enumerate_cfg_space(cfg_space);
}
+ printf("\n");
kfree(cfg_space);
}
diff --git a/kernel/src/main.c b/kernel/src/main.c
index 2e142ca..ceba990 100644
--- a/kernel/src/main.c
+++ b/kernel/src/main.c
@@ -41,14 +41,12 @@ int kernel_main(mb2_tag_header *multiboot_bootinfo, uint32_t multiboot_magic)
init_mutex(&serial_stdio_lock);
/* framebuffer is enabled from this point */
init_pmm();
- memory_usage();
init_keyboard();
init_timer(TICKS_PER_SECOND);
init_idt();
disc_init();
ext2_init();
init_tss();
- list_sys_tables();
parse_madt();
apic_remap_interrupts();
enable_interrupts();
diff --git a/kernel/src/mem/pmm.c b/kernel/src/mem/pmm.c
index d0c8a9f..e79cccf 100644
--- a/kernel/src/mem/pmm.c
+++ b/kernel/src/mem/pmm.c
@@ -42,7 +42,7 @@ void init_pmm()
void memory_usage()
{
- printf("memory used: %dMB\n",
+ printf("memory used: %dMB",
(MEM_USED_BELOW + (all_mem_cnt - free_mem_cnt) * PAGE_SIZE) /
1024 / 1024);
printf("memory free: %dMB\n", free_mem_cnt * PAGE_SIZE / 1024 / 1024);
diff --git a/kernel/src/scheduler/ap_startup.c b/kernel/src/scheduler/ap_startup.c
index 92fc51c..d2baaec 100644
--- a/kernel/src/scheduler/ap_startup.c
+++ b/kernel/src/scheduler/ap_startup.c
@@ -15,7 +15,7 @@ void ap_startup(void)
__asm__ __volatile__("pause;");
}
- printf("curr_cpu_apic_id: 0x%x\n", curr_cpu_apic_id());
+ /* printf("curr_cpu_apic_id: 0x%x\n", curr_cpu_apic_id()); */
lock(cnt_lock);
ap_cnt++;
unlock(cnt_lock);