Further work in echfs and partition management

This commit is contained in:
streaksu 2020-01-22 01:55:40 +01:00
parent 9339c093fe
commit 85d6152025
6 changed files with 129 additions and 3 deletions

View File

@ -4,6 +4,7 @@
#include <drivers/disk.h>
#include <lib/real.h>
#include <lib/print.h>
#include <lib/mbr.h>
#define SECTOR_SIZE 512
@ -77,3 +78,13 @@ int read(int drive, void *buffer, uint64_t loc, uint64_t count) {
return 0;
}
int read_partition(int drive, int partition, void *buffer, uint64_t loc, uint64_t count) {
struct mbr_part part;
int ret = mbr_get_part(&part, drive, partition);
if (ret) {
return ret;
}
return read(drive, buffer, loc + (part.first_sect * 512), count);
}

View File

@ -6,5 +6,6 @@
int read_sector(int drive, void *buffer, uint64_t lba, uint64_t count);
int read(int drive, void *buffer, uint64_t loc, uint64_t count);
int read_partition(int drive, int partition, void *buffer, uint64_t loc, uint64_t count);
#endif

74
src/fs/echfs.c Normal file
View File

@ -0,0 +1,74 @@
#include <fs/echfs.h>
#include <stdint.h>
#include <lib/libc.h>
#include <lib/print.h>
struct echfs_identity_table {
uint8_t jmp[4];
uint8_t signature[8];
uint64_t block_count;
uint64_t dir_length;
uint64_t block_size;
} __attribute__((packed));
struct echfs_dir_entry {
uint64_t parent_id;
uint8_t type;
char name[201];
uint64_t atime;
uint64_t mtime;
uint16_t perms;
uint16_t owner;
uint16_t group;
uint64_t ctime;
uint64_t payload;
uint64_t size;
} __attribute__((packed));
#define ROOT_DIR_ID (~((uint64_t)0))
#define END_OF_CHAIN (~((uint64_t)0))
#define FILE_TYPE 0
int load_echfs_file(int disk, int partition, void *buffer, const char *filename) {
// Read the S U P E R B L O C K.
struct echfs_identity_table id_table;
read_partition(disk, partition, &id_table, 0, sizeof(struct echfs_identity_table));
// Check the signature.
if (strncmp(id_table.signature, "_ECH_FS_", 8)) {
return -1;
}
// Variables from the table.
const uint64_t block_size = id_table.block_size;
const uint64_t block_count = id_table.block_count;
const uint64_t dir_length = id_table.dir_length;
// Calculate the offset, jumping the Allocation table and reserved blocks.
int offset = (16 * block_size) + (block_count * sizeof(uint64_t) / block_size);
// Find the file in the root dir.
struct echfs_dir_entry entry;
for (int i = offset; i < dir_length * block_size; i += sizeof(struct echfs_dir_entry)) {
read_partition(disk, partition, &entry, i, sizeof(struct echfs_dir_entry));
if (!strcmp(filename, entry.name) && entry.parent_id == ROOT_DIR_ID && entry.type == FILE_TYPE) {
goto FOUND;
}
}
return -1;
FOUND:;
// Load the file.
for (uint64_t i = entry.payload; i != END_OF_CHAIN;) {
// Read block.
read_partition(disk, partition, buffer, i * block_size, block_size);
buffer += block_size;
// Read the next block.
read_partition(disk, partition, &i, (16 * block_size) + i * sizeof(uint64_t), sizeof(uint64_t));
}
return 0;
}

6
src/fs/echfs.h Normal file
View File

@ -0,0 +1,6 @@
#ifndef __ECHFS_H__
#define __ECHFS_H__
int load_echfs_file(int disk, int partition, void *buffer, const char *filename);
#endif

View File

@ -22,6 +22,11 @@ int mbr_get_part(struct mbr_part *part, int drive, int partition) {
return ret;
}
// Check if the partition exists, fail if it doesnt.
if (entry.type == 0) {
return -1;
}
// Assign the final fields and return.
part->first_sect = entry.first_sect;
part->sect_count = entry.sect_count;

View File

@ -9,24 +9,53 @@ asm (
#include <lib/real.h>
#include <lib/print.h>
#include <lib/types.h>
#include <lib/mbr.h>
#include <fs/echfs.h>
extern symbol bss_begin;
extern symbol bss_end;
#define QWORD_KERNEL "qword.bin"
void main(int boot_drive) {
// Zero out .bss section
for (uint8_t *p = bss_begin; p < bss_end; p++)
*p = 0;
// Initial prompt.
init_vga_textmode();
print("qLoader 2\n\n");
print("=> Boot drive: %x\n\n", boot_drive);
for (;;) {
// Enumerate partitions.
struct mbr_part parts[4];
for (int i = 0; i < 4; i++) {
print("=> Checking for partition %d...", i);
int ret = mbr_get_part(&parts[i], boot_drive, i);
if (ret) {
print("Not found!\n");
} else {
print("Found!\n");
}
}
// Load the file from the chooen partition at 1 MiB.
int part = 1; // TODO: The boot partition is hardcoded for now.
print("=> Booting %s in partition %d\n", QWORD_KERNEL, part);
load_echfs_file(boot_drive, part, (void *)0x100000, QWORD_KERNEL);
// Boot the kernel.
asm volatile (
"jmp 0x100000"
:
: "b" ("")
: "memory"
);
/*for (;;) {
struct rm_regs r = {0};
rm_int(0x16, &r, &r); // Real mode interrupt 16h
char c = (char)(r.eax & 0xff);
text_write(&c, 1);
}
}*/
}