mirror of
https://github.com/DragonOS-Community/DragonOS.git
synced 2025-06-18 08:06:32 +00:00
bugfix: 修复了无法在除pid=0的进程以外的进程刷新帧缓冲区的bug
This commit is contained in:
@ -8,9 +8,9 @@ extern void (*interrupt_table[24])(void);
|
||||
|
||||
void init_8259A()
|
||||
{
|
||||
// 初始化中断门, 中断使用第二个ist
|
||||
// 初始化中断门, 中断使用第0个ist
|
||||
for(int i=32;i<=55;++i)
|
||||
set_intr_gate(i, 2, interrupt_table[i-32]);
|
||||
set_intr_gate(i, 0, interrupt_table[i-32]);
|
||||
kinfo("Initializing 8259A...");
|
||||
|
||||
// 初始化主芯片
|
||||
|
@ -68,6 +68,18 @@ void HPET_handler(uint64_t number, uint64_t param, struct pt_regs *regs)
|
||||
if (container_of(list_next(&timer_func_head.list), struct timer_func_list_t, list)->expire_jiffies <= timer_jiffies)
|
||||
set_softirq_status((1 << TIMER_SIRQ));
|
||||
|
||||
// if (current_pcb->pid == 2)
|
||||
// kwarn("timer_jiffies = %ld video_refresh_expire_jiffies=%ld", timer_jiffies, video_refresh_expire_jiffies);
|
||||
if (timer_jiffies >= video_refresh_expire_jiffies)
|
||||
{
|
||||
raise_softirq(VIDEO_REFRESH_SIRQ);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (video_last_refresh_pid != current_pcb->pid)
|
||||
raise_softirq(VIDEO_REFRESH_SIRQ);
|
||||
}
|
||||
|
||||
sched_update_jiffies();
|
||||
|
||||
break;
|
||||
@ -142,6 +154,8 @@ int HPET_init()
|
||||
HPET_NUM_TIM_CAP = (tmp >> 8) & 0x1f; // 读取计时器数量
|
||||
|
||||
// kinfo("HPET CLK_PERIOD=%#03lx Frequency=%f", HPET_COUNTER_CLK_PERIOD, (double)HPET_freq);
|
||||
kdebug("HPET_freq=%ld", (long)HPET_freq);
|
||||
// kdebug("HPET_freq=%lf", HPET_freq);
|
||||
|
||||
struct apic_IO_APIC_RTE_entry entry;
|
||||
// 使用I/O APIC 的IRQ2接收hpet定时器0的中断
|
||||
@ -149,6 +163,7 @@ int HPET_init()
|
||||
|
||||
// 计算HPET0间隔多少个时钟周期触发一次中断
|
||||
uint64_t clks_to_intr = 0.001 * HPET0_INTERVAL * HPET_freq;
|
||||
// kdebug("clks_to_intr=%#ld", clks_to_intr);
|
||||
if (clks_to_intr <= 0 || clks_to_intr > (HPET_freq * 8))
|
||||
{
|
||||
kBUG("HPET0: Numof clocks to generate interrupt is INVALID! value=%lld", clks_to_intr);
|
||||
|
@ -7,7 +7,7 @@
|
||||
uint64_t volatile timer_jiffies = 0; // 系统时钟计数
|
||||
|
||||
// 计算接下来n毫秒对应的系统时间片
|
||||
#define cal_next_n_ms_jiffies(expire_ms) (timer_jiffies + expire_ms / 5 + expire_ms % HPET0_INTERVAL ? 1 : 0)
|
||||
#define cal_next_n_ms_jiffies(expire_ms) (timer_jiffies + expire_ms / 5 + (expire_ms % HPET0_INTERVAL ? 1 : 0))
|
||||
|
||||
void timer_init();
|
||||
|
||||
|
@ -7,10 +7,15 @@
|
||||
#include <mm/mm.h>
|
||||
#include <mm/slab.h>
|
||||
#include <process/spinlock.h>
|
||||
#include <exception/softirq.h>
|
||||
|
||||
// 每个时刻只能有1个进程新增定时任务
|
||||
spinlock_t video_timer_func_add_lock;
|
||||
|
||||
#define REFRESH_INTERVAL 15 // 启动刷新帧缓冲区任务的时间间隔
|
||||
uint64_t video_refresh_expire_jiffies = 0;
|
||||
uint64_t video_last_refresh_pid = -1;
|
||||
|
||||
#define REFRESH_INTERVAL 15UL // 启动刷新帧缓冲区任务的时间间隔
|
||||
|
||||
ul VBE_FB_phys_addr; // 由bootloader传来的帧缓存区的物理地址
|
||||
struct screen_info_t
|
||||
@ -68,19 +73,15 @@ void init_frame_buffer(bool level)
|
||||
* @brief 刷新帧缓冲区
|
||||
*
|
||||
*/
|
||||
static void video_refresh_framebuffer()
|
||||
void video_refresh_framebuffer(void *data)
|
||||
{
|
||||
|
||||
// kdebug("pid%d flush fb", current_pcb->pid);
|
||||
// 暂时设置一个很大的值作为屏障,防止二次进入该区域(造成#GP)
|
||||
video_refresh_expire_jiffies = timer_jiffies + 100000;
|
||||
video_last_refresh_pid = current_pcb->pid;
|
||||
softirq_ack(VIDEO_REFRESH_SIRQ);
|
||||
|
||||
memcpy((void *)sc_info.fb_vaddr, (void *)sc_info.double_fb_vaddr, (sc_info.length << 2));
|
||||
|
||||
// 新增下一个刷新定时任务
|
||||
struct timer_func_list_t *tmp = (struct timer_func_list_t *)kmalloc(sizeof(struct timer_func_list_t), 0);
|
||||
spin_lock(&video_timer_func_add_lock);
|
||||
timer_func_init(tmp, &video_refresh_framebuffer, NULL, 10 * REFRESH_INTERVAL);
|
||||
timer_func_add(tmp);
|
||||
spin_unlock(&video_timer_func_add_lock);
|
||||
video_refresh_expire_jiffies = cal_next_n_ms_jiffies(REFRESH_INTERVAL);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -99,8 +100,15 @@ int video_init(bool level)
|
||||
// 启用双缓冲后,使能printk滚动动画
|
||||
// printk_enable_animation();
|
||||
// 初始化第一个屏幕刷新任务
|
||||
struct timer_func_list_t *tmp = (struct timer_func_list_t *)kmalloc(sizeof(struct timer_func_list_t), 0);
|
||||
timer_func_init(tmp, &video_refresh_framebuffer, NULL, REFRESH_INTERVAL);
|
||||
timer_func_add(tmp);
|
||||
// struct timer_func_list_t *tmp = (struct timer_func_list_t *)kmalloc(sizeof(struct timer_func_list_t), 0);
|
||||
// timer_func_init(tmp, &video_refresh_framebuffer, NULL, 10*REFRESH_INTERVAL);
|
||||
// timer_func_add(tmp);
|
||||
register_softirq(VIDEO_REFRESH_SIRQ, &video_refresh_framebuffer, NULL);
|
||||
kdebug("15/5=%#ld", 15 / 5);
|
||||
kdebug("1212121=%#ld", REFRESH_INTERVAL / 5);
|
||||
kdebug("sdds21=%#ld", REFRESH_INTERVAL / 5 + (REFRESH_INTERVAL % HPET0_INTERVAL ? 1 : 0));
|
||||
video_refresh_expire_jiffies = cal_next_n_ms_jiffies(10 * REFRESH_INTERVAL);
|
||||
kdebug("video_refresh_expire_jiffies=%ld", video_refresh_expire_jiffies);
|
||||
raise_softirq(VIDEO_REFRESH_SIRQ);
|
||||
}
|
||||
}
|
@ -9,4 +9,9 @@
|
||||
* true ->高级初始化:增加double buffer的支持
|
||||
* @return int
|
||||
*/
|
||||
int video_init(bool level);
|
||||
int video_init(bool level);
|
||||
|
||||
extern uint64_t video_refresh_expire_jiffies;
|
||||
extern uint64_t video_last_refresh_pid;
|
||||
|
||||
extern void video_refresh_framebuffer();
|
Reference in New Issue
Block a user