Skip to content

Commit 4e066fd

Browse files
撤下 free service 机制以修复多核下发生保护性异常的问题.
vfs 增加文件系统元数据结构体, 将init进程调用从 shell 移动到 kmain. 添加 openfs umount2 readlink sysinfo getgid getppid 系统调用. Co-authored-by: suhuajun-github <115517663+suhuajun-github@users.noreply.github.com>
1 parent ac4a485 commit 4e066fd

File tree

14 files changed

+449
-297
lines changed

14 files changed

+449
-297
lines changed

assets/initramfs.img

6.8 MB
Binary file not shown.

src/x86_64/cpu/smp.c

Lines changed: 7 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -120,12 +120,15 @@ _Noreturn void apu_entry() {
120120
apu_idle->cpu_timer = nano_time();
121121
apu_idle->cpu_id = current_cpu->id;
122122
apu_idle->status = RUNNING;
123+
apu_idle->fs = apu_idle->gs = 0;
124+
apu_idle->fs_base = read_fsbase();
125+
apu_idle->gs_base = read_gsbase();
123126
char name[50];
124127
sprintf(name, "CP_IDLE_CPU%u", current_cpu->id);
125128
memcpy(apu_idle->name, name, strlen(name));
126-
apu_idle->name[strlen(name)] = '\0';
127-
current_cpu->idle_pcb = apu_idle;
128-
current_cpu->ready = true;
129+
apu_idle->name[strlen(name)] = '\0';
130+
current_cpu->idle_pcb = apu_idle;
131+
current_cpu->ready = true;
129132
change_current_tcb(apu_idle);
130133
apu_idle->parent_group = kernel_group;
131134
apu_idle->group_index = queue_enqueue(kernel_group->pcb_queue, apu_idle);
@@ -145,8 +148,6 @@ _Noreturn void apu_entry() {
145148

146149
setup_syscall(false);
147150

148-
create_kernel_thread((void *)halt_service, NULL, "free service", kernel_group, lapic_id());
149-
150151
open_interrupt;
151152
loop __asm__ volatile("hlt");
152153
}
@@ -180,7 +181,7 @@ void smp_setup() {
180181
__asm__ volatile("pause" ::: "memory");
181182
}
182183

183-
current_cpu->idle_pcb = kernel_head_task;
184+
current_cpu->idle_pcb = kernel_head_task;
184185
kernel_head_task->queue_index =
185186
queue_enqueue(((smp_cpu_t *)read_kgsbase())->scheduler_queue, kernel_head_task);
186187
if (kernel_head_task->queue_index == (size_t)-1) {
@@ -203,7 +204,5 @@ void smp_setup() {
203204
insert_sched_entity(((struct eevdf_t *)current_cpu->sched_handle)->root, idle_entity);
204205
eevdf_sched->current = idle_entity;
205206
open_interrupt;
206-
207-
create_kernel_thread((void *)halt_service, NULL, "free_service", kernel_group, lapic_id());
208207
kinfo("%d processors have been enabled.", cpu_count);
209208
}

src/x86_64/fs/cpio/cpfs.c

Lines changed: 25 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -170,13 +170,37 @@ errno_t cpfs_symlink(void *parent, const char *name, vfs_node_t node) {
170170
return EOK;
171171
}
172172

173+
static void free_child_node(cpfs_file_t *parent, cpfs_file_t *dir) {
174+
if (dir->is_dir) {
175+
do {
176+
cpfs_file_t *tmp = NULL;
177+
cpfs_file_t *pos, *n;
178+
llist_for_each(pos, n, &dir->child_node, curr_node) {
179+
tmp = pos;
180+
}
181+
if (tmp == NULL) break;
182+
free_child_node(dir, tmp);
183+
free(dir);
184+
} while (true);
185+
return;
186+
}
187+
llist_delete(&dir->curr_node);
188+
free(dir->data);
189+
free(dir);
190+
}
191+
192+
void cpfs_unmount(void *root) {
193+
cpfs_file_t *handle = root;
194+
free_child_node(NULL, handle);
195+
}
196+
173197
static int dummy() {
174198
return -ENOSYS;
175199
}
176200

177201
static struct vfs_callback cpfs_callbacks = {
178202
.mount = cpfs_mount,
179-
.unmount = (void *)empty,
203+
.unmount = cpfs_unmount,
180204
.mkdir = cpfs_mkdir,
181205
.close = cpfs_close,
182206
.stat = cpfs_stat,

src/x86_64/fs/vfs.c

Lines changed: 19 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -10,18 +10,23 @@
1010
#include "kprint.h"
1111
#include "krlibc.h"
1212
#include "list.h"
13+
#include "llist.h"
1314
#include "pcb.h"
1415
#include "pipefs.h"
1516

1617
vfs_node_t rootdir = NULL;
1718

1819
static void empty_func() {}
1920

20-
struct vfs_callback vfs_empty_callback;
21+
struct vfs_callback vfs_empty_callback;
22+
struct vfs_filesystem vfs_empty_filesystem;
2123

2224
vfs_callback_t fs_callbacks[256] = {
2325
[0] = &vfs_empty_callback,
2426
};
27+
28+
struct llist_header fs_metadata_list;
29+
2530
static int fs_nextid = 1;
2631

2732
#define callbackof(node, _name_) (fs_callbacks[(node)->fsid]->_name_)
@@ -256,9 +261,14 @@ int vfs_regist(const char *name, vfs_callback_t callback) {
256261
for (size_t i = 0; i < sizeof(struct vfs_callback) / sizeof(void *); i++) {
257262
if (((void **)callback)[i] == NULL) return VFS_STATUS_FAILED;
258263
}
259-
int id = fs_nextid++;
260-
264+
int id = fs_nextid++;
261265
fs_callbacks[id] = callback;
266+
267+
vfs_filesystem_t filesystem = malloc(sizeof(struct vfs_filesystem));
268+
filesystem->callback = callback;
269+
strcpy(filesystem->name, name);
270+
llist_init_head(&filesystem->node);
271+
llist_append(&fs_metadata_list, &filesystem->node);
262272
return id;
263273
}
264274

@@ -477,6 +487,11 @@ errno_t vfs_unmount(const char *path) {
477487
return VFS_STATUS_FAILED;
478488
}
479489

490+
size_t vfs_readlink(vfs_node_t node, char *buf, size_t bufsize) {
491+
size_t ret = callbackof(node, readlink)(node, buf, 0, bufsize);
492+
return ret;
493+
}
494+
480495
void *general_map(vfs_read_t read_callback, void *file, uint64_t addr, uint64_t len, uint64_t prot,
481496
uint64_t flags, uint64_t offset) {
482497
pcb_t current_task = get_current_task()->parent_group;
@@ -580,7 +595,7 @@ bool vfs_init() {
580595
for (size_t i = 0; i < sizeof(struct vfs_callback) / sizeof(void *); i++) {
581596
((void **)&vfs_empty_callback)[i] = (void *)empty_func;
582597
}
583-
598+
llist_init_head(&fs_metadata_list);
584599
rootdir = vfs_node_alloc(NULL, "/");
585600
rootdir->type = file_dir;
586601
kinfo("Virtual File System initialize.");

src/x86_64/include/killer.h

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,5 @@
33
#include "pcb.h"
44

55
void add_death_proc(pcb_t task);
6-
void halt_service();
76

87
void killer_setup();

src/x86_64/include/shell.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,4 +3,7 @@
33
#define MAX_COMMAND_LEN 100
44
#define MAX_ARG_NR 50
55

6+
bool exec(int argc, char **argv);
7+
void mount(int argc, char **argv);
8+
69
_Noreturn void shell_setup();

src/x86_64/include/syscall.h

Lines changed: 62 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,45 @@
1111
#define SYSCALL_FAULT_(name) ((uint64_t)-(name))
1212
#define FD_SETSIZE 1024
1313

14-
#define syscall_(name) \
14+
// 一个非常取巧的宏魔法, 可以简化 syscall 函数的定义
15+
#define __EXPAND_PARAMS(...) __VA_ARGS__
16+
#define __CONCAT_IMPL(a, b) a##b
17+
#define __CONCAT(a, b) __CONCAT_IMPL(a, b)
18+
19+
#define __ARGS_COUNT_IMPL(_0, _1, _2, _3, _4, _5, _6, N, ...) N
20+
21+
#define __ARGS_COUNT(...) __EXPAND_PARAMS(__ARGS_COUNT_IMPL(__VA_ARGS__, 6, 5, 4, 3, 2, 1, 0))
22+
23+
#define __SYSCALL_IMPL_0(NAME) \
24+
uint64_t syscall_##NAME(uint64_t arg0, uint64_t arg1, uint64_t arg2, uint64_t arg3, \
25+
uint64_t arg4, uint64_t arg5, struct syscall_regs *regs)
26+
27+
#define __SYSCALL_IMPL_1(NAME, P1) \
28+
uint64_t syscall_##NAME(P1, uint64_t arg1, uint64_t arg2, uint64_t arg3, uint64_t arg4, \
29+
uint64_t arg5, struct syscall_regs *regs)
30+
31+
#define __SYSCALL_IMPL_2(NAME, P1, P2) \
32+
uint64_t syscall_##NAME(P1, P2, uint64_t arg2, uint64_t arg3, uint64_t arg4, uint64_t arg5, \
33+
struct syscall_regs *regs)
34+
35+
#define __SYSCALL_IMPL_3(NAME, P1, P2, P3) \
36+
uint64_t syscall_##NAME(P1, P2, P3, uint64_t arg3, uint64_t arg4, uint64_t arg5, \
37+
struct syscall_regs *regs)
38+
39+
#define __SYSCALL_IMPL_4(NAME, P1, P2, P3, P4) \
40+
uint64_t syscall_##NAME(P1, P2, P3, P4, uint64_t arg4, uint64_t arg5, struct syscall_regs *regs)
41+
42+
#define __SYSCALL_IMPL_5(NAME, P1, P2, P3, P4, P5) \
43+
uint64_t syscall_##NAME(P1, P2, P3, P4, P5, uint64_t arg5, struct syscall_regs *regs)
44+
45+
#define __SYSCALL_IMPL_6(NAME, P1, P2, P3, P4, P5, P6) \
46+
uint64_t syscall_##NAME(P1, P2, P3, P4, P5, P6, struct syscall_regs *regs)
47+
48+
#define __SYSCALL_DISPATCH(N, NAME, ...) __CONCAT(__SYSCALL_IMPL_, N)(NAME, ##__VA_ARGS__)
49+
50+
#define syscall_(NAME, ...) __SYSCALL_DISPATCH(__ARGS_COUNT(0, ##__VA_ARGS__), NAME, ##__VA_ARGS__)
51+
52+
#define syscall_def_(name) \
1553
uint64_t syscall_##name( \
1654
uint64_t arg0 __attribute__((unused)), uint64_t arg1 __attribute__((unused)), \
1755
uint64_t arg2 __attribute__((unused)), uint64_t arg3 __attribute__((unused)), \
@@ -114,12 +152,16 @@
114152
#define SYSCALL_LINK 86
115153
#define SYSCALL_UNLINK 87
116154
#define SYSCALL_SYMLINK 88
155+
#define SYSCALL_READLINK 89
156+
#define SYSCALL_SYSINFO 99
117157
#define SYSCALL_GETUID 102
158+
#define SYSCALL_GETGID 104
118159
#define SYSCALL_SETUID 105
119160
#define SYSCALL_SETGID 106
120161
#define SYSCALL_GETEUID 107
121162
#define SYSCALL_GETEGID 108
122163
#define SYSCALL_SETPGID 109
164+
#define SYSCALL_GETPPID 110
123165
#define SYSCALL_GETGROUPS 115
124166
#define SYScall_GETPGID 121
125167
#define SYSCALL_SIGSUSPEND 130
@@ -128,6 +170,7 @@
128170
#define SYSCALL_ARCH_PRCTL 158
129171
#define SYSCALL_G_AFFINITY 160
130172
#define SYSCALL_MOUNT 165
173+
#define SYSCALL_UMOUNT2 166
131174
#define SYSCALL_REBOOT 169
132175
#define SYSCALL_GET_TID 186
133176
#define SYSCALL_FUTEX 202
@@ -146,6 +189,7 @@
146189
#define SYSCALL_PIPE2 293
147190
#define SYSCALL_CP_F_RANGE 326
148191
#define SYSCALL_STATX 332
192+
#define SYSCALL_FSOPEN 430
149193
#define SYSCALL_FACCESSAT2 439
150194

151195
// CoolPotOS 平台特有系统调用号定义
@@ -287,6 +331,23 @@ struct statx {
287331
/* 0x100 */
288332
};
289333

334+
struct sysinfo {
335+
int64_t uptime; /* Seconds since boot */
336+
uint64_t loads[3]; /* 1, 5, and 15 minute load averages */
337+
uint64_t totalram; /* Total usable main memory size */
338+
uint64_t freeram; /* Available memory size */
339+
uint64_t sharedram; /* Amount of shared memory */
340+
uint64_t bufferram; /* Memory used by buffers */
341+
uint64_t totalswap; /* Total swap space size */
342+
uint64_t freeswap; /* swap space still available */
343+
uint16_t procs; /* Number of current processes */
344+
uint16_t pad; /* Explicit padding for m68k */
345+
uint64_t totalhigh; /* Total high memory size */
346+
uint64_t freehigh; /* Available high memory size */
347+
uint32_t mem_unit; /* Memory unit size in bytes */
348+
char _f[20 - 2 * sizeof(uint64_t) - sizeof(uint32_t)]; /* Padding: libc5 uses this.. */
349+
};
350+
290351
struct cpos_meminfo {
291352
uint64_t used; // 已用内存
292353
uint64_t available; // 未使用内存

src/x86_64/include/vfs.h

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,7 @@
6464

6565
#include "ctype.h"
6666
#include "list.h"
67+
#include "llist.h"
6768

6869
typedef struct vfs_node *vfs_node_t;
6970

@@ -132,6 +133,12 @@ typedef struct vfs_callback { // VFS回调函数
132133
vfs_rename_t rename; // 重命名文件或文件夹
133134
} *vfs_callback_t;
134135

136+
typedef struct vfs_filesystem {
137+
vfs_callback_t callback;
138+
char name[10];
139+
struct llist_header node;
140+
} *vfs_filesystem_t;
141+
135142
struct vfs_node { // vfs节点
136143
vfs_node_t parent; // 父目录
137144
vfs_node_t linkto; // 符号链接指向的节点
@@ -167,6 +174,7 @@ struct fd {
167174

168175
extern struct vfs_callback vfs_empty_callback;
169176
extern vfs_node_t rootdir;
177+
extern struct llist_header fs_metadata_list;
170178

171179
/**
172180
* 创建目录节点
@@ -253,6 +261,15 @@ vfs_node_t vfs_open(const char *str);
253261
*/
254262
errno_t vfs_ioctl(vfs_node_t device, size_t options, void *arg);
255263

264+
/**
265+
* 读取一个符号链接文件
266+
* @param node 文件节点
267+
* @param buf 缓冲区
268+
* @param bufsize
269+
* @return
270+
*/
271+
size_t vfs_readlink(vfs_node_t node, char *buf, size_t bufsize);
272+
256273
bool is_virtual_fs(const char *src);
257274

258275
vfs_node_t vfs_do_search(vfs_node_t dir, const char *name);

src/x86_64/main.c

Lines changed: 41 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,8 @@
6060
# define GIT_VERSION "unknown"
6161
#endif
6262

63+
#define INITRAMFS_START 1
64+
6365
void kmain();
6466

6567
extern void error_setup(); // error_handle.c
@@ -82,6 +84,20 @@ _Noreturn void cp_reset() {
8284
loop;
8385
}
8486

87+
static void kernel_watchdog() {
88+
kwarn("PID 1 process has exited, user session is missing.");
89+
kwarn("Should the kernel be restarted?");
90+
printk("Reboot kernel(Y/n): ");
91+
_terminal_flush();
92+
do {
93+
char c = kernel_getch();
94+
printk("%c\n", c);
95+
_terminal_flush();
96+
if (c == '\n' || c == 'y') { cp_reset(); }
97+
if (c == 'n') break;
98+
} while (true);
99+
}
100+
85101
void kmain() {
86102
gdt_setup();
87103
idt_setup();
@@ -144,15 +160,37 @@ void kmain() {
144160
netfs_setup();
145161
load_all_kernel_module();
146162
partition_init();
163+
#ifdef INITRAMFS_START
147164
cpio_init();
165+
#endif
148166
kinfo("Kernel load Done!");
149167

150-
pcb_t shell_group = create_process_group("Shell Service", NULL, NULL, "", NULL, NULL, 0);
151-
create_kernel_thread((void *)shell_setup, NULL, "KernelShell", shell_group, SIZE_MAX);
168+
// pcb_t shell_group = create_process_group("Shell Service", NULL, NULL, "", NULL, NULL, 0);
169+
// create_kernel_thread((void *)shell_setup, NULL, "KernelShell", shell_group, SIZE_MAX);
152170

153171
open_interrupt;
154172
enable_scheduler();
155-
change_bsp_weight();
156173

174+
#ifdef INITRAMFS_START
175+
# if 0
176+
int argc = 3;
177+
char *argv[] = {"/init", NULL};
178+
exec(argc, argv);
179+
# else
180+
{
181+
int argc = 3;
182+
char *argv_init[2] = {"exec", "/sbin/init"};
183+
char *argv_sh[3] = {"exec", "/bin/busybox", "sh"};
184+
char *argv_bash[2] = {"exec", "/bin/bash"};
185+
//exec(argc, argv_init);
186+
exec(argc, argv_bash);
187+
exec(argc, argv_sh);
188+
}
189+
# endif
190+
191+
#endif
192+
kernel_watchdog();
193+
194+
change_bsp_weight();
157195
loop __asm__ volatile("hlt");
158196
}

src/x86_64/mem/bitmap.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -236,5 +236,5 @@ void init_frame_bitmap() {
236236
frame_allocator.origin_frames = origin_frames;
237237
frame_allocator.usable_frames = origin_frames - bitmap_frame_count;
238238

239-
logkf("Available memory: %lld MiB\n", (origin_frames / 256));
239+
logkf("Available memory: %lld MiB bitmap_sz: %llu\n", (origin_frames / 256), bitmap_size);
240240
}

0 commit comments

Comments
 (0)