增加简单的sema&mutex支持
This commit is contained in:
@@ -11,3 +11,4 @@ msg_tag_t factory_create_thread(obj_handler_t obj, vpage_t vpage);
|
||||
msg_tag_t factory_create_thread_vcpu(obj_handler_t obj, vpage_t vpage);
|
||||
msg_tag_t factory_create_task(obj_handler_t obj, vpage_t vpage);
|
||||
msg_tag_t facotry_create_share_mem(obj_handler_t obj, vpage_t vpage, umword_t size);
|
||||
msg_tag_t facotry_create_sema(obj_handler_t obj, vpage_t vpage, int cnt, int max);
|
||||
|
||||
@@ -15,6 +15,7 @@ enum kobj_prot
|
||||
IRQ_PROT,
|
||||
SHARE_MEM_PROT, // 10
|
||||
VMA_PROT,
|
||||
SEMA_PROT,
|
||||
MAX_PROT,
|
||||
};
|
||||
|
||||
|
||||
7
mkrtos_user/lib/sys/inc/u_sema.h
Normal file
7
mkrtos_user/lib/sys/inc/u_sema.h
Normal file
@@ -0,0 +1,7 @@
|
||||
#pragma once
|
||||
|
||||
#include "u_prot.h"
|
||||
#include "u_hd_man.h"
|
||||
|
||||
msg_tag_t u_sema_up(obj_handler_t obj);
|
||||
msg_tag_t u_sema_down(obj_handler_t obj);
|
||||
@@ -105,3 +105,22 @@ msg_tag_t facotry_create_share_mem(obj_handler_t obj, vpage_t vpage, umword_t si
|
||||
|
||||
return tag;
|
||||
}
|
||||
msg_tag_t facotry_create_sema(obj_handler_t obj, vpage_t vpage, int cnt, int max)
|
||||
{
|
||||
register volatile umword_t r0 asm(ARCH_REG_0);
|
||||
|
||||
mk_syscall(syscall_prot_create(FACTORY_CREATE_KOBJ, FACTORY_PROT, obj).raw,
|
||||
0,
|
||||
SEMA_PROT,
|
||||
vpage.raw,
|
||||
cnt,
|
||||
max,
|
||||
0);
|
||||
asm __volatile__(""
|
||||
:
|
||||
:
|
||||
: ARCH_REG_0);
|
||||
msg_tag_t tag = msg_tag_init(r0);
|
||||
|
||||
return tag;
|
||||
}
|
||||
|
||||
39
mkrtos_user/lib/sys/src/u_sema.c
Normal file
39
mkrtos_user/lib/sys/src/u_sema.c
Normal file
@@ -0,0 +1,39 @@
|
||||
#include "u_types.h"
|
||||
#include "u_prot.h"
|
||||
#include "u_arch.h"
|
||||
|
||||
enum SEMA_OP
|
||||
{
|
||||
SEMA_UP,
|
||||
SEMA_DOWN,
|
||||
};
|
||||
msg_tag_t u_sema_up(obj_handler_t obj)
|
||||
{
|
||||
register volatile umword_t r0 asm(ARCH_REG_0);
|
||||
|
||||
mk_syscall(syscall_prot_create(SEMA_UP, SEMA_PROT, obj).raw,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0);
|
||||
msg_tag_t tag = msg_tag_init(r0);
|
||||
|
||||
return tag;
|
||||
}
|
||||
msg_tag_t u_sema_down(obj_handler_t obj)
|
||||
{
|
||||
register volatile umword_t r0 asm(ARCH_REG_0);
|
||||
|
||||
mk_syscall(syscall_prot_create(SEMA_DOWN, SEMA_PROT, obj).raw,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0);
|
||||
msg_tag_t tag = msg_tag_init(r0);
|
||||
|
||||
return tag;
|
||||
}
|
||||
@@ -1,6 +1,6 @@
|
||||
cmake_minimum_required(VERSION 3.13)
|
||||
|
||||
file(GLOB deps src/*.c src/*.S)
|
||||
file(GLOB deps src/*.c src/*.S src/test/*.c)
|
||||
file(GLOB arch_src src/test/${ARCH_NAME}/*.c src/test/${ARCH_NAME}/*.S)
|
||||
|
||||
add_executable(init.elf
|
||||
|
||||
@@ -36,6 +36,8 @@
|
||||
static void test(void)
|
||||
{
|
||||
#if 0
|
||||
u_sema_test();
|
||||
u_sema_test2();
|
||||
ipi_test();
|
||||
ipc_test();
|
||||
ipc_test2();
|
||||
|
||||
@@ -1,197 +0,0 @@
|
||||
#include "u_log.h"
|
||||
#include "u_prot.h"
|
||||
#include "u_mm.h"
|
||||
#include "u_factory.h"
|
||||
#include "u_thread.h"
|
||||
#include "u_task.h"
|
||||
#include "u_ipc.h"
|
||||
#include "u_hd_man.h"
|
||||
#include "u_task.h"
|
||||
#include <assert.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <u_sleep.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#define DEBUG_IPC_CALL 1
|
||||
//! 读取系统寄存器
|
||||
#define read_sysreg(reg) ({ \
|
||||
unsigned long _val; \
|
||||
asm volatile("mrs %0, " #reg \
|
||||
: "=r"(_val)); \
|
||||
_val; \
|
||||
})
|
||||
static inline int get_cpu_id(void)
|
||||
{
|
||||
return read_sysreg(mpidr_el1) & 0xff; // 读取该寄存器获取处理器id
|
||||
}
|
||||
|
||||
static umword_t th1_hd = 0;
|
||||
static umword_t th2_hd = 0;
|
||||
static umword_t th3_hd = 0;
|
||||
static umword_t th4_hd = 0;
|
||||
|
||||
static __attribute__((aligned(4096))) char msg_buf0[4096];
|
||||
static __attribute__((aligned(4096))) char msg_buf1[4096];
|
||||
static __attribute__((aligned(4096))) char msg_buf2[4096];
|
||||
static __attribute__((aligned(4096))) char msg_buf3[4096];
|
||||
#define STACK_SIZE 2048
|
||||
static __attribute__((aligned(8))) uint8_t stack0[STACK_SIZE];
|
||||
static __attribute__((aligned(8))) uint8_t stack1[STACK_SIZE];
|
||||
static __attribute__((aligned(8))) uint8_t stack2[STACK_SIZE];
|
||||
static __attribute__((aligned(8))) uint8_t stack3[STACK_SIZE];
|
||||
|
||||
static void hard_sleep(void)
|
||||
{
|
||||
|
||||
for (volatile int i; i < 10000000; i++)
|
||||
;
|
||||
}
|
||||
static int test_cn = 0;
|
||||
static int to_cpu[4];
|
||||
|
||||
static void thread_test_func(void)
|
||||
{
|
||||
char *buf;
|
||||
umword_t len;
|
||||
|
||||
printf("%s:%d thread 0 init.\n", __func__, __LINE__);
|
||||
while (1)
|
||||
{
|
||||
|
||||
to_cpu[0] = rand() % 4;
|
||||
|
||||
printf("thread 0 to %d cpu.\n", to_cpu[0]);
|
||||
thread_run_cpu(th1_hd, 2, to_cpu[0]);
|
||||
assert(to_cpu[0] == get_cpu_id());
|
||||
|
||||
test_cn++;
|
||||
}
|
||||
}
|
||||
static void thread_test_func2(void)
|
||||
{
|
||||
char *buf;
|
||||
umword_t len;
|
||||
|
||||
printf("%s:%d thread 1 init.\n", __func__, __LINE__);
|
||||
while (1)
|
||||
{
|
||||
to_cpu[1] = rand() % 4;
|
||||
|
||||
printf("thread 1 to %d cpu.\n", to_cpu[1]);
|
||||
thread_run_cpu(th2_hd, 2, to_cpu[1]);
|
||||
assert(to_cpu[1] == get_cpu_id());
|
||||
|
||||
test_cn++;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
static void thread_test_func3(void)
|
||||
{
|
||||
|
||||
printf("%s:%d thread 2 init.\n", __func__, __LINE__);
|
||||
while (1)
|
||||
{
|
||||
to_cpu[2] = rand() % 4;
|
||||
|
||||
printf("thread 2 to %d cpu.\n", to_cpu[2]);
|
||||
thread_run_cpu(th3_hd, 2, to_cpu[2]);
|
||||
assert(to_cpu[2] == get_cpu_id());
|
||||
|
||||
test_cn++;
|
||||
|
||||
}
|
||||
}
|
||||
static void thread_test_func4(void)
|
||||
{
|
||||
|
||||
printf("%s:%d thread 3 init.\n", __func__, __LINE__);
|
||||
while (1)
|
||||
{
|
||||
to_cpu[3] = rand() % 4;
|
||||
|
||||
printf("thread 3 to %d cpu.\n", to_cpu[3]);
|
||||
thread_run_cpu(th4_hd, 2, to_cpu[3]);
|
||||
assert(to_cpu[3] == get_cpu_id());
|
||||
|
||||
test_cn++;
|
||||
|
||||
}
|
||||
}
|
||||
/**
|
||||
* @brief 启动两个线程并进行ipc测试
|
||||
*
|
||||
*/
|
||||
void ipi_test(void)
|
||||
{
|
||||
msg_tag_t tag;
|
||||
th1_hd = handler_alloc();
|
||||
assert(th1_hd != HANDLER_INVALID);
|
||||
th2_hd = handler_alloc();
|
||||
assert(th2_hd != HANDLER_INVALID);
|
||||
th3_hd = handler_alloc();
|
||||
assert(th3_hd != HANDLER_INVALID);
|
||||
|
||||
memset(msg_buf0, 0, sizeof(msg_buf0));
|
||||
memset(msg_buf1, 0, sizeof(msg_buf1));
|
||||
memset(msg_buf2, 0, sizeof(msg_buf2));
|
||||
memset(msg_buf3, 0, sizeof(msg_buf3));
|
||||
|
||||
tag = factory_create_thread(FACTORY_PROT, vpage_create_raw3(KOBJ_ALL_RIGHTS, 0, th1_hd));
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_bind_task(th1_hd, TASK_THIS);
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_msg_buf_set(th1_hd, msg_buf0);
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_exec_regs(th1_hd, (umword_t)thread_test_func, (umword_t)stack0 + STACK_SIZE, TASK_RAM_BASE(), 0);
|
||||
task_set_obj_name(TASK_THIS, th1_hd, "cli_th");
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_run_cpu(th1_hd, 2, 0);
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = factory_create_thread(FACTORY_PROT, vpage_create_raw3(KOBJ_ALL_RIGHTS, 0, th2_hd));
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_bind_task(th2_hd, TASK_THIS);
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_msg_buf_set(th2_hd, msg_buf1);
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_exec_regs(th2_hd, (umword_t)thread_test_func2, (umword_t)stack1 + STACK_SIZE, TASK_RAM_BASE(), 0);
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
task_set_obj_name(TASK_THIS, th2_hd, "cli0_th");
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_run_cpu(th2_hd, 2, 0);
|
||||
|
||||
tag = factory_create_thread(FACTORY_PROT, vpage_create_raw3(KOBJ_ALL_RIGHTS, 0, th3_hd));
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_bind_task(th3_hd, TASK_THIS);
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_msg_buf_set(th3_hd, msg_buf2);
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_exec_regs(th3_hd, (umword_t)thread_test_func3, (umword_t)stack2 + STACK_SIZE, TASK_RAM_BASE(), 0);
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
task_set_obj_name(TASK_THIS, th3_hd, "cli1_th");
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_run_cpu(th3_hd, 2, 0);
|
||||
|
||||
tag = factory_create_thread(FACTORY_PROT, vpage_create_raw3(KOBJ_ALL_RIGHTS, 0, th4_hd));
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_bind_task(th4_hd, TASK_THIS);
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_msg_buf_set(th4_hd, msg_buf3);
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_exec_regs(th4_hd, (umword_t)thread_test_func4, (umword_t)stack3 + STACK_SIZE, TASK_RAM_BASE(), 0);
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
task_set_obj_name(TASK_THIS, th4_hd, "cli2_th");
|
||||
assert(msg_tag_get_prot(tag) >= 0);
|
||||
tag = thread_run_cpu(th4_hd, 2, 0);
|
||||
|
||||
while (test_cn < 1000)
|
||||
;
|
||||
// task_unmap(TASK_THIS, vpage_create_raw3(KOBJ_DELETE_RIGHT, 0, th1_hd));
|
||||
// task_unmap(TASK_THIS, vpage_create_raw3(KOBJ_DELETE_RIGHT, 0, th2_hd));
|
||||
// task_unmap(TASK_THIS, vpage_create_raw3(KOBJ_DELETE_RIGHT, 0, th3_hd));
|
||||
// task_unmap(TASK_THIS, vpage_create_raw3(KOBJ_DELETE_RIGHT, 0, th4_hd));
|
||||
|
||||
}
|
||||
76
mkrtos_user/server/init/src/test/sema_test.c
Normal file
76
mkrtos_user/server/init/src/test/sema_test.c
Normal file
@@ -0,0 +1,76 @@
|
||||
|
||||
#include "u_factory.h"
|
||||
#include "u_sema.h"
|
||||
#include "u_hd_man.h"
|
||||
#include "u_task.h"
|
||||
#include <assert.h>
|
||||
#include <pthread.h>
|
||||
#include <stdio.h>
|
||||
int u_sema_test(void)
|
||||
{
|
||||
msg_tag_t tag;
|
||||
obj_handler_t sema_hd;
|
||||
|
||||
sema_hd = handler_alloc();
|
||||
assert(sema_hd != HANDLER_INVALID);
|
||||
tag = facotry_create_sema(FACTORY_PROT, vpage_create_raw3(KOBJ_ALL_RIGHTS, 0, sema_hd), 0, 1);
|
||||
assert(msg_tag_get_val(tag) >= 0);
|
||||
|
||||
u_sema_up(sema_hd);
|
||||
u_sema_down(sema_hd);
|
||||
|
||||
handler_free_umap(sema_hd);
|
||||
return 0;
|
||||
}
|
||||
#include <u_sleep.h>
|
||||
static pthread_t pth1;
|
||||
static pthread_t pth2;
|
||||
static pthread_t pth3;
|
||||
static obj_handler_t sema_hd2;
|
||||
|
||||
static void *thread_th1(void *arg)
|
||||
{
|
||||
while (1)
|
||||
{
|
||||
printf("sema_up start\n");
|
||||
u_sema_up(sema_hd2);
|
||||
u_sleep_ms(100);
|
||||
printf("sema_up end\n");
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
static void *thread_th2(void *arg)
|
||||
{
|
||||
while (1)
|
||||
{
|
||||
printf("sema_down start\n");
|
||||
u_sema_down(sema_hd2);
|
||||
u_sleep_ms(50);
|
||||
printf("sema_down end\n");
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
static void *thread_th3(void *arg)
|
||||
{
|
||||
while (1)
|
||||
{
|
||||
printf("sema_down2 start\n");
|
||||
u_sema_down(sema_hd2);
|
||||
u_sleep_ms(50);
|
||||
printf("sema_down2 end\n");
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
int u_sema_test2(void)
|
||||
{
|
||||
msg_tag_t tag;
|
||||
|
||||
sema_hd2 = handler_alloc();
|
||||
assert(sema_hd2 != HANDLER_INVALID);
|
||||
tag = facotry_create_sema(FACTORY_PROT,
|
||||
vpage_create_raw3(KOBJ_ALL_RIGHTS, 0, sema_hd2), 0, 1);
|
||||
assert(msg_tag_get_val(tag) >= 0);
|
||||
pthread_create(&pth1, NULL, thread_th1, NULL);
|
||||
pthread_create(&pth1, NULL, thread_th2, NULL);
|
||||
pthread_create(&pth3, NULL, thread_th3, NULL);
|
||||
}
|
||||
@@ -23,3 +23,5 @@ void malloc_test(void);
|
||||
void thread_cpu_test(void);
|
||||
int thread_vcpu_test(void);
|
||||
void ipi_test(void);
|
||||
int u_sema_test(void);
|
||||
int u_sema_test2(void);
|
||||
|
||||
@@ -1,52 +0,0 @@
|
||||
.text
|
||||
.global thread_vcpu_test_fn
|
||||
.type thread_vcpu_test_fn,%function
|
||||
thread_vcpu_test_fn:
|
||||
//mrs x0, ttbr0_el1
|
||||
mov x0,x0
|
||||
tlbi vmalle1 // Invalidate local TLB
|
||||
dsb nsh
|
||||
mov x0, #0x30000000
|
||||
msr vbar_el1, x0
|
||||
mov x0, #0x40000000
|
||||
msr ttbr0_el1, x0
|
||||
msr ttbr1_el1, x0
|
||||
isb
|
||||
mov x0, #0
|
||||
msr spsr_el1, x0
|
||||
|
||||
mov x0, #1
|
||||
mrs x1, SCTLR_EL1
|
||||
orr x1, x1, x0
|
||||
msr SCTLR_EL1, x1
|
||||
isb
|
||||
ic iallu
|
||||
dsb nsh
|
||||
isb
|
||||
mrs x0, CurrentEL
|
||||
|
||||
mov x0, #0
|
||||
msr spsr_el1, x0
|
||||
adr x0, el0_entry
|
||||
// mov x0, #0x80000
|
||||
msr elr_el1, x0
|
||||
eret
|
||||
el0_entry:
|
||||
//mrs x0, sp_el0
|
||||
mov x0, #0x10000000
|
||||
str x1, [x0]
|
||||
mrs x0, TTBR0_EL2
|
||||
mov x0, x1
|
||||
mov x0, x1
|
||||
mov x0, x1
|
||||
mov x0, x1
|
||||
mov x0, x1
|
||||
mov x0, x1
|
||||
mov x0, x1
|
||||
// wfe //!<陷入内核
|
||||
// wfi
|
||||
|
||||
b .
|
||||
|
||||
|
||||
|
||||
@@ -1,71 +0,0 @@
|
||||
|
||||
#include <u_thread.h>
|
||||
#include <u_hd_man.h>
|
||||
#include <u_task.h>
|
||||
#include <errno.h>
|
||||
#include <u_prot.h>
|
||||
#include <u_factory.h>
|
||||
#include <u_vmam.h>
|
||||
#include <string.h>
|
||||
|
||||
#define STACK_SIZE 4096
|
||||
static __attribute__((aligned(8))) uint8_t stack0[STACK_SIZE];
|
||||
|
||||
extern void thread_vcpu_test_fn(void);
|
||||
|
||||
int thread_vcpu_test(void)
|
||||
{
|
||||
msg_tag_t tag;
|
||||
|
||||
obj_handler_t th1_hd;
|
||||
umword_t msg_buf_addr;
|
||||
int ret;
|
||||
|
||||
th1_hd = handler_alloc();
|
||||
if (th1_hd == HANDLER_INVALID)
|
||||
{
|
||||
return -ENOENT;
|
||||
}
|
||||
tag = factory_create_thread_vcpu(FACTORY_PROT, vpage_create_raw3(KOBJ_ALL_RIGHTS, 0, th1_hd));
|
||||
if (msg_tag_get_prot(tag) < 0)
|
||||
{
|
||||
handler_free(th1_hd);
|
||||
return msg_tag_get_prot(tag);
|
||||
}
|
||||
tag = u_vmam_alloc(VMA_PROT, vma_addr_create(VPAGE_PROT_RW, 0, 0),
|
||||
PAGE_SIZE, 0, (addr_t *)(&msg_buf_addr));
|
||||
if (msg_tag_get_val(tag) < 0)
|
||||
{
|
||||
ret = msg_tag_get_val(tag);
|
||||
goto end;
|
||||
}
|
||||
memset((void *)msg_buf_addr, 0, PAGE_SIZE);
|
||||
|
||||
tag = thread_exec_regs(th1_hd, (umword_t)thread_vcpu_test_fn,
|
||||
(umword_t)stack0 + STACK_SIZE - sizeof(void *),
|
||||
TASK_RAM_BASE(), 0);
|
||||
if (msg_tag_get_prot(tag) < 0)
|
||||
{
|
||||
ret = msg_tag_get_prot(tag);
|
||||
goto end_free_mm;
|
||||
}
|
||||
tag = thread_bind_task(th1_hd, TASK_THIS);
|
||||
if (msg_tag_get_prot(tag) < 0)
|
||||
{
|
||||
goto end_free_mm;
|
||||
}
|
||||
tag = thread_msg_buf_set(th1_hd, (void *)msg_buf_addr);
|
||||
if (msg_tag_get_prot(tag) < 0)
|
||||
{
|
||||
goto end_free_mm;
|
||||
}
|
||||
thread_run(th1_hd, 2); // 优先级默认为2
|
||||
ret = 0;
|
||||
goto end_ok;
|
||||
end_free_mm:
|
||||
u_vmam_free(VMA_PROT, msg_buf_addr, PAGE_SIZE);
|
||||
end:
|
||||
handler_free_umap(th1_hd);
|
||||
end_ok:
|
||||
return ret;
|
||||
}
|
||||
Reference in New Issue
Block a user