Commit Graph
56 Commits
Author SHA1 Message Date
TermiNexus e0308ba074 feat(input): 键盘接入 app —— 焦点回退 + 无聚焦控件时路由到文本控件
① explorer:新增 _key_target(),focused 无效(-1/已关/已最小化)时回退到 z 序最高的可见窗口,不再把键盘输入整体丢弃;载荷经核对无需改(explorer 传 evt.x,vpui.Text 读的正是 evt.x)。② vpui:Tk 新增 _first_text_widget(),mainloop 的 KEY 分支在 focused_widget 为空时回退到第一个可见的 Text/Entry,并同步置焦点;顺带修 Text.handle_event 只认 '\\r' 导致回车无效(内核给的是 '\\n')。Terminal 无需改动。
2026-10-17 12:00:19 +08:00
TermiNexus 51ce473092 feat(explorer): 任务栏窗口图标可点击激活/恢复
原来任务栏图标只画不响应:鼠标按下分支只做窗口 hit_test,点在任务栏上返回 -1 就什么都不做。新增 _taskbar_icon_x/_taskbar_icon_y/_taskbar_icon_hit/_activate_from_taskbar:几何与绘制共用同一套函数(避免热区与绘制分叉),筛选与 ordinal 顺序和 _draw_taskbar_rows 完全一致(used && active,含 minimized)。按下时先判 taskbar 图标命中 —— 命中则激活:minimized 先恢复并置脏,再走既有 focus()(更新 z 序、聚焦、整体置脏);未命中才继续原有窗口命中/拖动逻辑,本次点击不会被重复处理。
2026-10-17 11:55:22 +08:00
TermiNexus 0593f1798b fix(explorer): 窗口创建/销毁时整体置脏,避免内容残留
抽出 mark_all_windows()(所有可见窗口整体置脏,含阴影带),CREATE 与 DESTROY 分支各调用一次并保留 mark_titles()。原来这两处只标记标题栏 + 任务栏:新建窗口的内容区不脏(可能空白),关窗后下方露出的旧内容也不会重画,都要等鼠标经过才恢复。focus() 的内联循环同步收敛到该函数。
2026-10-17 11:53:14 +08:00
TermiNexus fbbb10099d fix(explorer): 焦点/层级切换时把可见窗口整体置脏
现象:窗口层级切换后内容不刷新,要等鼠标经过才覆盖。原因:focus() 只调 mark_titles()(标题栏 + 任务栏),没有标记内容区;被抬起的窗口内容区因此不会重画,原来压在上面的窗口仍留在屏幕。改为层级变化时对所有可见窗口调 mark_win(含阴影带),随后按新 z 序整体重画。
2026-10-17 11:52:17 +08:00
TermiNexus a19c5d1a53 perf(explorer): 修半透明/圆角混合底,并优化阴影与混合热点
① 混合底:上一版背景裁剪会跳过窗口覆盖的列,导致 back 在那些列保留上一帧内容;而 WIN7 标题栏 alpha 混合、WIN11/XP 圆角逐像素裁剪都需要读到正确背景。现在按样式在必要行补铺背景:WIN7 铺标题栏行 + 底部圆角段,WIN11/XP 铺上下圆角段,CLASSIC/WIN10 不铺(直角不透明)。补铺发生在所有窗口绘制之前,下层窗口随后正常覆盖。② 性能:阴影 alpha 改按行查表 + 无除法 SWAR 变暗;_blend/_blend_row 改 SWAR 并行混合(无除法、无格式分支);内容行不再先整行 fill 再 blit,直接 blit + 左右 1px 边框;圆角行逐像素只保留左右各 r 列,中段整段拷贝(宽 800 窗每圆角行从约 800 次降到 16 次);关闭键圆角先扫连续区间再整段 fill;render_range 缓存每个可见窗口的几何/样式,_top_z 只算一次并传入。
2026-10-17 11:36:34 +08:00
TermiNexus 844fbff31c fix(kernel,explorer): 内核不再画屏消除残留;CREATE 打印 style 诊断
蓝色残留根因:main.vp 里 VGA_drv.Print 在 __init__ 尾部执行,而它晚于 app spawn —— explorer 已经把桌面画上去了,内核随后又往 framebuffer 打一行测试文本/清屏,于是永远盖在桌面上(整屏刷一次也救不了,因为之后又被画)。S3e 之后屏幕由 explorer 独占合成,直接删除内核侧 VGA 驱动创建与 Print。另:handle_request 的 CREATE 分支加一条诊断打印(style/w/h),用于确认 style 是否真的透传到 explorer —— 5 条日志,定位后撤。
2026-10-17 11:03:05 +08:00
TermiNexus ae39fab5d8 perf(explorer): 背景只铺窗口外区间;进主循环前整屏刷一次
① 修卡:render_range 原来对每一行都先铺整行背景(全宽)再画窗口,对窗口覆盖的那几百列纯属浪费 —— Scene3D 每帧刷全窗时等于每帧多拷一整屏背景。改为逐行只铺没被任何可见窗口覆盖的 x 区间(窗口收集与 z 排序提到背景之前)。② 修 VGA 残留:内核启动期的 VGA/gfx 测试内容(蓝色测试块)不属于任何脏行,只靠增量渲染会永远留在屏幕上;serve() 进主循环前先 mark_all + 整屏渲染一次。
2026-10-16 23:07:09 +08:00
TermiNexus 78b0ca8db7 feat(explorer): 窗口样式差异可见化(标题栏/边框圆角/按钮按样式区分)
参考 desktop.vp 的 _draw_app_window 与三枚按钮函数,把 5 种样式的差异做到一眼可辨:标题栏 CLASSIC 蓝紫纯色 / WIN10 近黑 / WIN11 深灰 / WIN7 浅蓝 Aero 渐变(alpha 玻璃) / WINXP 蓝渐变;边框 CLASSIC-win10 直角、WIN7/11/XP 圆角 r=8;按钮 CLASSIC 16x16 深蓝底灰 X、WIN10/11 46x30 无底色灰字形、WIN7 28x20、WINXP 21x21 且红底白 X。新增 _is_in_corner/_is_on_border/_corner_alpha 与按行绘制的 _draw_flat_row/_draw_round_row/_blend_row/_title_row_color;关闭键热区改为与绘制共用同一套几何函数,避免点击错位。标题栏高度仍统一用 TITLE_H=32:app 侧内容区高度依赖 vpui 的 TITLE_H,改高度会让内容错位,故差异只由配色/圆角/按钮体现。
2026-10-16 23:04:21 +08:00
TermiNexus aab4643dfa feat(desk): style 透传到 CREATE 请求;任务栏随焦点/窗口集合刷新
① style 透传:DeskMsg 增加 style 字段(放在 d 与 title 之间),window._send 增加 style 可选参数(默认 0,其它调用点不受影响),create_window 把 style 一并压进 CREATE 请求,explorer 的 handle_request 用它建窗(原来硬编码 0)—— 这样 vpui 的 set_style 才能真正生效,样式区分与圆角才有意义。DeskMsg 是共享协议结构,app 与 explorer 必须一起重编。② 任务栏刷新:mark_titles 追加标记任务栏条带(焦点切换会调它,任务栏图标配色随之更新),CREATE 与 DESTROY 分支也各调一次(图标数量变化)。
2026-10-16 22:42:58 +08:00
TermiNexus c4ff870941 perf(explorer): 恢复逐脏段渲染与提交,避免退化成全屏重绘
上一版把脏行合并成一段连续范围渲染 + 一次提交,导致窗口(上)与任务栏(下)同时脏时每帧全屏渲染 + 全屏 4MB 提交,帧率崩。改回逐个脏段处理:每段先渲染进 back,随后逐行提交该段,段内一致性仍然成立,而写屏总量回到与脏区面积成正比。
2026-10-16 22:37:46 +08:00
TermiNexus 5f863bed71 perf(explorer): 合成改画后备缓冲,渲染末尾只提交脏行到 framebuffer
消除撕裂:原来所有绘制直接写真实 framebuffer,与显示器扫描并发 ⇒ 撕裂/闪烁;而用户态无法做垂直同步(QEMU/OVMF 的 GOP 线性帧缓冲没有 VGA 回扫信号,FB_WAIT_VBLANK 实测返回 0 空转)。改法对齐历史内核桌面的做法:DeskServer 增加进程本地后备缓冲 back(与 bg_row 同机制 mmap 匿名页),row_fill/row_blit/draw_char/阴影混合/任务栏 logo 等所有写入点从 self.fb 改到 self.back(back 行距 = fb_w,framebuffer 行距 = pitch_px),render() 先把脏行范围渲染到 back,末尾再把仍脏的行逐行 memcpy 提交到 framebuffer。分配失败时打印并退回直写。同时删掉已完成使命的 vblank iters 诊断打印。
2026-10-16 22:31:35 +08:00
TermiNexus 3945decc2d fix(explorer): 窗口覆盖到底部条带时把任务栏一并置脏
现象:任务栏要鼠标经过(光标行恰好落在它上面)才刷新一行。因为任务栏只在启动的 mark_all 画过一次,之后没有时钟每秒标脏,唯一能让任务栏行变脏的是窗口变化或光标自身所在行。窗口在 render_range 里是画在任务栏**之上**的,所以窗口覆盖到底部条带时必须连带标记任务栏条带,否则残留旧窗口内容、也无法恢复。
2026-10-16 22:17:25 +08:00
TermiNexus e1d31c3dc9 diag(explorer,fb0): vblank 返回等待迭代数并打点;脏行合并为一段渲染
排查'仍闪烁':① FB_WAIT_VBLANK 改为返回等待消耗的迭代数(到上限 = 超时 = 当前没有 VGA 回扫信号),explorer 首次调用打印一次 —— 用来判定垂直回扫同步是否真的生效;② render() 原来按连续脏行分段、每段各渲染一次,同一帧的多次写屏会跨越多个扫描周期,现在把脏行合并成一段连续范围一次性渲染,缩小撕裂窗口。
2026-10-16 21:55:36 +08:00
TermiNexus ecabd59518 feat(explorer): 还原窗口样式、阴影、任务栏与三枚窗口按钮,精简注释
对齐被删除的内核桌面 desktop.vp 的视觉:窗口改为四边框 + 标题栏(活动/非活动配色)+ 标题内容分隔线 + 内容按 1px 内缩合成,并按 WinSlot.style 选择样式配色;新增最小化/最大化/关闭三枚按钮;新增矩形窗口阴影(SHADOW_* + self._blend 按 framebuffer 格式做 alpha 混合);任务栏改为深色底 + 分 opper线 + 蓝色 logo 圆盘 + ViperOS 文本 + 每个活动窗口的带边框图标(焦点/普通/最小化三色)与标题首字符,高度 28→50 对齐旧桌面。置脏范围改用 mark_win(含阴影带)/ mark_titles(活动窗口切换时刷新所有标题栏)。同时精简全文注释(不保留历史沿革叙述)。任务栏时钟未实现:用户态无时间源;圆角未实现:style 尚未透传到 CREATE 请求;最小化/最大化仅外观未接线。
2026-10-16 21:47:44 +08:00
TermiNexus e41701e201 feat(fb0): 新增 FB_WAIT_VBLANK ioctl,合成前等垂直回扫
explorer 直接写 framebuffer 会与显示器扫描并发,造成撕裂/闪烁;而它在 Ring3 没有 IO 端口权限,不能像历史内核桌面那样自己 inb 0x3DA。所以在 /dev/fb0 上加 FB_WAIT_VBLANK(0x4601)由内核代等垂直回扫(带超时,无 VGA 时序时不死等),vpsdk 暴露 fb_wait_vblank(),desk_server.render() 写屏前调用一次。
2026-10-16 21:37:58 +08:00
TermiNexus 1c0720a746 perf(explorer,vpui): 矩形填充改 rep stosd,鼠标输入一次取完队列
性能三处:① vpui._fill_rect 原为逐像素双重循环(带边界判断),app 每帧都要把整窗填一遍背景色(Scene3D 是 640×360 = 23 万次写),改为逐行 string.memset32(rep stosd),先统一裁剪再整行填充;② explorer.row_fill 同样逐像素,任务栏(1360 像素/行)与标题栏每帧要填上万像素,同样改 rep stosd;③ 鼠标延迟:poll_input 原来每轮只从设备取一个包,而 serve 一轮要跑 poll_requests + poll_input + render(毫秒级),PS/2 是 100Hz ⇒ 输入在队列里排队累积、光标明显滞后。改为一次把已到的包全部取完(位移累加、按键以最后一个包为准),并把位移累加+钳制抽成 _move_cursor()。
2026-10-16 21:31:04 +08:00
TermiNexus 6eb000d01d fix(mouse): 鼠标设备改返回相对位移,光标位置归 explorer 累积
现场:鼠标一有输入,光标立刻跳到左上角。根因:devfs 的 mouse_device.read 在 size>=9 时填的是 mouse.get_x()/get_y(),而 mouse_x/mouse_y 这两个静态量从未被更新(irq_handler 只把解码后的包入队 packets[]),恒为 0;explorer 拿到 (0,0) 就照抄成光标位置。改法:内核只给出 PS/2 包里的相对位移 dx/dy(uint8 原始字节手工做有符号扩展,不依赖 int8 转换语义),光标位置作为 explorer 自己的状态累积并做边界钳制 —— 内核不知道屏幕几何,钳制本来就该在图形壳这一层。
2026-10-16 21:23:05 +08:00
TermiNexus 14568e49e5 fix(explorer): 光标改用 desktop.vp 历史里的 16x16 位图模板
上一版的三角是临时凑的形状,这里改回被删实现里的正规模板:16×16 位图掩码,0 = 透明(不写像素,背景由 render_range 先重画窗口内容恢复,移动不留残影)、1 = 黑边、2 = 白心。模板逐字取自 VKernel/Kernel/services/desktop.vp(S3e 删除前,git 13eee8e^)的 _CURSOR_ARROW;绘制时把同一行连续同色像素合并成一次 row_fill,并处理光标越出左右边界时的裁剪。同一历史文件里另有 _CURSOR_IBEAM / _CURSOR_RESIZE_EW / _CURSOR_RESIZE_NS / _CURSOR_RESIZE_NWSE 四套模板,将来接上 WinSlot.cursor 即可启用(注释里已记录出处)。
2026-10-16 21:18:06 +08:00
TermiNexus 7536cc6fdb fix(explorer): 光标换成指针形状,替换原来的 10x10 白框黑心方块
原实现是 row_fill 画一个 10x10 白方块再把中间 6x6 挖成黑,视觉上是个方框而不是鼠标指针。改为顶点在左上、逐行向右下加宽 1 像素的实心三角(12x12),白边 + 黑心;形状外的像素一个都不写,背景由 render_range 先重画窗口内容恢复,所以移动不留残影。脏行标记的高度同步从 CURSOR_SZ 换成 CURSOR_H。
2026-10-16 21:15:39 +08:00
TermiNexus a35896e36e test(explorer): 首次鼠标包打点,区分内核无中断与收到包未处理 2026-10-16 20:57:56 +08:00
TermiNexus 2f20cf42aa fix(vpui): 建窗失败改为可见错误上报;Scene3D 加分步诊断打点
背景:Tk.mainloop 的循环条件是 window.is_active(win_id),而 is_active 对 win_id < 0 直接返回 0 ⇒ 一旦 create_window 失败,app 一次循环都不进、一句日志都不打就 process.exit(0)(现场:Scene3D spawn 后静默退出,「没有窗口」就是这么来的)。改动:window.vp 的 _attach / _connect / create_window 四个失败返回点补 [win] 错误上报(open 失败 / mmap 失败 / desk 未就绪超时 / 请求环压入失败 / CREATED 超时),这些是错误可见性而非临时噪音,长期保留;Scene3D/main.vp 加 _dbg 分步打点(start / tk ok / canvas ok / scene ok / geometry 后的 win_id 与 buf / 渲染线程 / mainloop 返回),用于定位它到底死在哪一步,定位完成后撤除。
2026-10-16 20:51:07 +08:00
TermiNexus 0fd1bf7567 fix(fb0): 几何登记为 0 + FbInfo 按值返回只回传一半 —— explorer 拿不到 framebuffer 几何
现场(serial.log 330-339):[fb0] ioctl fd=6 req=0x4600 arg=0x7fffffdffb78 w=0 h=0 ⇒ request 与 arg 传递都正常、写入回读也正常,真正的问题是设备对象里的 fb_w/fb_h/fb_pitch/fb_format/fb_phys/fb_size 全为 0;随后 explorer 以 pitch=0 调 mmap 失败退出。两个独立缺陷:① 内核侧——devfs_register_fb0 收到的是被清零的 width/height/pitch/fb_format/fb_size(main.vp 顶部注释记录的"__init__ 的 fb/width/height/pitch 局部量被偶发写坏"同类问题:这些长寿命局部量在 L121 之后、L304 之前被写坏,而 L366+ 的 _CheckFrameLocals 又不报,属时点相关),改为在调用点直接从 BootInfo 重取几何并补一条 _CheckFrameLocals(pre_devfs_fb0);② SDK 侧——fb_get_info 按值返回 32 字节 FbInfo,现场表现为只有前 16 字节有效、后 16 字节是调用方栈残留(size=1802724708 phys=0x130c30),改为出参 out + 返回 ioctl 返回码;③ explorer 侧改为判返回码与 pitch/size 非 0,失败即 _dbg 说明原因后 fail-fast 退出,不再带着 0 几何继续。
2026-10-16 20:20:36 +08:00
TermiNexus 1fc1fab1e1 feat(explorer): S3f —— 补用户态字体渲染:窗口标题文字 + 任务栏底板
字体表直接复用 vpsdk/vpui.vp 的 font(8x16 点阵、MSB 优先、row = font[ci][fy]),不另抄第二份;新增 draw_char/draw_str。

合成器:① 窗口标题栏画上该窗口的 title(标题在建窗时随 CREATE 消息内联进槽位,set_title 走 REQ_TITLE 更新);② 屏幕底部 28px 任务栏底板 + "ViperOS" 标签,绘制次序为 背景 → 任务栏 → 窗口(窗口可盖住任务栏,与旧内核桌面同序)。

仍未做:任务栏时钟(用户态暂无时间源,需要 /dev/rtc 之类)、窗口侧边框与样式区分、最小化、拖边缩放、崩溃进程的窗口回收。
2026-10-16 19:28:08 +08:00
TermiNexus d96362186f fix(explorer): push_event/push_event_pid 补齐第 6 个参数 d,修 llvm.call 操作数个数错
现象:f4160f3611036a68.ll 报 llvm.call 传了 7 个操作数、被调方期望 6。根因是我这边实参个数不一致:签名是 (self,win,etype,a,b,c)(self+5=6),而鼠标三处调用按"再带一个 buttons"写了 6 个实参(self+6=7)。DeskMsg 本来就有 a..d 四个载荷位,window.vp 也早已用 _evt.d 当 button,所以正确修法是把签名补上 d:push_event/push_event_pid 各加一个 d 参数,并把原先少传的 KEY/CLOSE/CREATED 三处补齐。

说明:这不是编译器实现问题 —— 编译器(LLVM verifier)报得准确;只是实参个数这类错误没在前端拦住、漏到了 LLVM 层,属于前端检查的缺口,可另案记录。
2026-10-16 19:24:09 +08:00
TermiNexus 5e1cd04478 feat(s4): 删除 SERIAL_PUTS 私有 syscall,用户态改走 /dev/serial0
内核:删掉 SERIAL_PUTS 的枚举项/派发分支/处理函数(内核自身的 serial.puts 是直接驱动调用,不受影响)。SDK:vpsdk/devfs.vp 新增 serial_puts()(惰性 open /dev/serial0 一次 + write),syscall.vp 删掉该成员。

调用点全部切到 devfs.serial_puts:vpsdk/stdio.vp 的 printf、vpsdk/vpui.vp 的 _serial_puts、Apps/Terminal 的 _sdbg、Apps/Explorer 的 _dbg、Libs/SerialLogger 的 log_info/log_warn(.so 同样走设备节点)。顺带清掉因此失效的 import(vpui 的 _syscall、Terminal 的 _syscall、Explorer 的 syscall)。

至此私有段只剩 7 项:TELL/SIZE/OPENDIR/READDIR/CLOSEDIR(可由 lseek/fstat/openat+getdents64 表达)与 LOAD_SO/SO_CALL1(动态库加载待下沉用户层)。
2026-10-16 19:17:39 +08:00
TermiNexus c5e107e361 fix(vpsdk): 修正 desk_open/desk_map 的模块前缀(链接 undefined symbol 根因)
现象:ld.lld 报 undefined symbol aeb1805c34e518f8.desk_map / desk_open,引用来自 window.vp 的对象(_attach/_connect)。根因:我在 window.vp 与 Explorer/main.vp 里把这两个函数挂到了 devfs. 前缀上,而它们的定义在 vpsdk/desk.vp(devfs.vp 里只有底层 shm_map)。编译器按名解析到 desk.vp 的声明并发出带 desk 前缀的符号,但调用点的前缀不一致 ⇒ 链接期解析不到。

同时清掉 window.vp 里已不再使用的 import(devfs/stdlib/syscall —— get_winbuf 改用共享区后 stdlib.malloc 与 syscall 都已无引用)。
2026-10-16 19:14:57 +08:00
TermiNexus 13eee8e8ea feat(s3e)!: 内核 UI 层整体下沉用户态 —— 删 11 个 UI syscall + services/desktop.vp
内核 intr/syscall.vp:删除 WAIT_WINDOW/CREATE_WINDOW/DRAW_TEXT/GET_WINBUF/WIN_FLUSH/POLL_EVENT/SET_CURSOR/SET_TITLE/SET_GEOMETRY/SET_RESIZABLE/GET_WIN_SIZE 的枚举项、派发分支与对应函数;去掉 services.desktop 依赖;EXIT 不再拆窗口(内核已不持有窗口语义)。

删除 VKernel/Kernel/services/desktop.vp(~2900 行内核桌面/合成/输入分发);main.vp 不再启动 desktop 线程,只保留一次 fb 局部量一致性校验。剩余 syscall = Linux 对齐段 + 8 个待 devfs 化的私有项(SERIAL_PUTS/TELL/SIZE/OPENDIR/READDIR/CLOSEDIR/LOAD_SO/SO_CALL1)。

SDK:yield_cpu() 从 WAIT_WINDOW(0,2) 改为 Linux 对齐的 sched_yield(内核同样是 try_reschedule);syscall.vp 同步删掉 11 个 UI 成员。

explorer:关闭按钮改为先通知 CLOSE 再把槽位 used=0 —— window.vp 的 is_active() 见 used==0 返回 0,app 的 while is_active() 自然退出;像素缓冲不复用(bump 分配)⇒ 无别名风险。至此输入只剩 explorer 一家在读(内核桌面已删),两个合成器之争结束。
2026-10-16 19:11:44 +08:00
TermiNexus a45b9808b0 feat(s3d): vpsdk/window.vp 改走 /dev/desk 共享协议(对外 API 一字未改)
window.vp 重写:不再走内核 UI syscall,全部经共享区与用户态 explorer 通信。对外函数名/签名/常量/InputEvent 全部保持原样 ⇒ vpui.vp 与四个 app 零改动。

数据面:get_winbuf 直接返回共享 arena 里本窗口那块像素缓冲的线性地址(app 就地画),flush 只压一条 FLUSH 请求 ⇒ 全程零像素拷贝(旧实现是 app 私有缓冲 + 整块拷给内核)。控制面:请求环 + 按 pid 分的事件环;is_active/get_win_size 直接读共享槽(零 syscall)。create_window 压 CREATE(标题内联在消息里)并等 CREATED 答复拿 win_id。

协议补齐:DeskMsg 增内联 title(CREATE/TITLE 用,ring_push/pop 同步搬运);事件环按 pid 分(不能按 win_id——建窗答复送不到;也不能单环——单消费者结构多 app 会互抢);新增 DESK_MOUSE_PRESS/RELEASE/HOVER 语义常量。

合成器:关闭按钮改为置 active=0(app 的 while is_active() 自然退出)并通知一次 CLOSE;点击只投给窗口**内容区**(标题栏用于拖动)、松手投 RELEASE、移动投 HOVER,坐标均换算成窗口内坐标;拖动改为只在标题栏生效;RESIZE 重新从 arena 切片并更新内容尺寸(与 vpui 的 bh = h - TITLE_H - 2 对齐)。
2026-10-16 19:08:18 +08:00
TermiNexus bb82c2fe75 fix(desk)!: 事件环改为单环+按 pid 过滤,并补 getpid(S3d 前置)
缺陷:原设计把事件环按 win_id 索引,但建窗答复 CREATED 必须在 app 知道 win_id 之前送达 —— 按 win_id 索引物理上不可能送达。改为**单一事件环**,每条事件带目标 pid,由 app 用自己的 pid 过滤(与内核旧接口 poll_event(buf, caller_pid) 同口径)。

DeskMsg 增 pid 字段(ring_push/ring_pop 同步搬运,漏搬则事件全被当成 pid=0);desk_evt_ring_off() 去掉 win_id 参数;desk_format 只初始化一个事件环;服务端 push_event 从窗口槽取 pid、建窗答复走新增的 push_event_pid(此时槽里还没有 pid)。

新增 GETPID(Linux 号 39,此前是"留空"项,现在真正实现):内核 GETPID() 返回 process.current(),SDK 侧 process.get_pid()。app 需要它才能过滤自己的窗口事件。
2026-10-16 18:58:43 +08:00
TermiNexus 1633769534 feat(explorer): S3c —— explorer 窗口服务端与合成器(请求环 + 输入 + 逐行合成)
Apps/Explorer/desk_server.vp(新增):窗口槽分配(含 arena 像素缓冲切分与底色预清)、Z 序与焦点、逐脏行合成(背景整行 memcpy → 各窗口按 Z 序只重画落在该行的那一段 → 光标)、请求处理(CREATE/DESTROY/MOVE/RESIZE/FLUSH/ACTIVATE)、事件投递(CREATED/CLOSE/KEY)、输入轮询(读 /dev/input/keyboard 的 ASCII 与 /dev/input/mouse 的按键+x/y,做命中测试、点击聚焦、标题栏右侧关闭按钮发 CLOSE、按住拖动移窗)。

main.vp:fb/desk/输入三者就绪后交给 DeskServer.serve() 主循环;去掉 S2 的渐变条演示(像素通路已由 fb 映射日志与合成器本身证明)。desk.vp:删掉写错且无人使用 的 DESK_MSG_SIZE 常量。

注意:本切片尚未实现标题文字(需用户态字体表)、任务栏、最小化/缩放、窗口侧边框与样式;且此过渡态下内核 desktop 与 explorer 同时在画屏幕,会互相覆盖 —— S3d(app 改走协议)与 S3e(删内核 UI)收口。
2026-10-16 18:56:30 +08:00
TermiNexus 30708d3250 feat(desk): S3 底座 —— /dev/desk 共享内存通道 + 用户态协议模块
内核 devfs 新增 shm_device(/dev/desk):同一物理区间映射给所有打开者;main.vp 启动时 mm.malloc 出 DESK_SHM_SIZE(8MB) 并登记,分配失败只打日志跳过(explorer 的 open 会明确失败,不静默兜底)。内核只负责"分配 + 共享映射",区间内布局完全不参与。

vpsdk/desk.vp(新增协议模块):共享区固定布局(DeskHeader / WinSlot / 请求环 / 每窗口事件环 / 像素 arena)、单生产者单消费者环形队列(head/tail,跨进程无锁、全程指针直读写)、explorer 用的 desk_format/desk_arena_alloc 与 app 用的 desk_ready。请求/事件类型常量齐备(CREATE/DESTROY/MOVE/RESIZE/TITLE/FLUSH/ACTIVATE 与 CREATED/CLOSE/KEY/MOUSE/RESIZE)。

vpsdk/devfs.vp 增 DEV_DESK 与 shm_map();Explorer 启动即 open+mmap /dev/desk、desk_format 初始化并打印头信息,验证 IPC 底座可用。
2026-10-16 18:53:27 +08:00
TermiNexus 6bd2390e08 feat(explorer): S2 —— 新增图形壳应用 explorer 骨架,用户态经 devfs+mmap 直接写屏
Apps/Explorer:复制标准 app 骨架(main.vp / linker.ld / project.vpj,链接地址 0x400000)。启动流程:open /dev/fb0 → ioctl(FB_GET_INFO) 打几何 → mmap 拿到线性地址 → 等约 2 秒(等内核桌面首屏全量重绘过去)→ 画一条渐变横条验证像素真上屏 → open /dev/input/keyboard|mouse 验证输入设备可达 → 常驻不退出。

vpsdk/devfs.vp(新增 SDK 设备层):设备路径常量(与内核注册名逐字一致)、FB_GET_INFO 与 FbInfo 镜像(packed,与内核同布局)、fb_open/fb_get_info/fb_map/kbd_open/mouse_open。

build.py:把 Explorer 加进 required_apps 清单与完整构建分支;内核 main.vp 在四个 app 之后 spawn /APPS/explorer.elf。内核 desktop 与 explorer 并存属迁移中间态,S3 会把窗口合成整体交出去。
2026-10-16 18:43:13 +08:00
TermiNexus ca72ddbbf7 refactor(syscall): 调用号改用 enum 并全面对齐 Linux x86-64 ABI
内核 intr/syscall.vp 与 vpsdk/syscall.vp 各一份 1..34 的 define 表改为同名 enum Syscall。编号口径:与 Linux 同名同号;Linux 有而我们未实现的留空不占号(12 brk / 39 getpid / 84 rmdir / 217 getdents64 / 257 openat … 需要时按号补)。

15 个语义重合的调用直接用 Linux 号:READ 0 / WRITE 1 / OPEN 2 / CLOSE 3 / STAT 4 / SEEK 8 / MMAP 9 / MUNMAP 11 / YIELD 24 / THREAD_CREATE 56(≈clone) / SPAWN 59(≈execve) / THREAD_EXIT 60(exit) / MKDIR 83 / REMOVE 87 / EXIT 231(exit_group)。

其余 19 个(UI 11 个 + SERIAL_PUTS/TELL/SIZE/OPENDIR/READDIR/CLOSEDIR/LOAD_SO/SO_CALL1)暂放 0x1000 起的**临时私有段**,每条带迁移标注:私有能力最终不占 syscall 号、改走 devfs 设备文件;UI 11 个待用户态 explorer(图形壳)接管 framebuffer 与输入后删除。

内核派发链改 n == int(Syscall.X)(n 是 int/i64、成员是 i32,显式 int() 规避未证实的混合宽度比较);SDK 全部调用点统一为 syscall.Syscall.X;stdlib 的 SYSCALL_MMAP 别名并入 Syscall.MMAP;Terminal 里硬编码的 uint64(18) 改为常量。
2026-10-16 18:32:33 +08:00
TermiNexus 0886252a08 feat(vpsdk): window/syscall/process/stdio/fs/dynlib 适配 + apps 同步调整 2026-10-16 16:40:41 +08:00
TermiNexus befed3904a fix(Gargantua): setup_camera 改用 V3 值语义(消除旧版 &_g_cam 指针残留),移除定位用调试输出 2026-10-16 14:12:50 +08:00
TermiNexus d9b39e99a5 chore(debug): Scene3D 每帧持续打印 time 与两个 sinf 采样值位模式 - 抓曲线变平时刻 2026-10-15 20:02:19 +08:00
TermiNexus d31f887290 chore(scene3d): 移除 [s3d] 时间探针 - 已确认回绕常量(-12.566371/+12.566371)正确、时间正常 2026-10-15 19:58:45 +08:00
TermiNexus cceefa4e2e revert(scene3d): PI 还原为 define - app 侧 workaround 撤销,float 字面量折叠由 ViperC 侧修复 2026-10-15 18:22:48 +08:00
TermiNexus aec563e33a fix(scene3d): PI 改为运行期 float 变量 - 消除 float 字面量被折叠成 double 致波形算术提升为 double(SIN 波形塌平) 2026-10-15 18:21:10 +08:00
TermiNexus 2803aff04c chore(debug): Scene3D 时间探针改为按 time 跨整数打印(与帧计数解耦) - 确保能可靠观测渲染循环是否在推进 2026-10-15 17:46:14 +08:00
TermiNexus e066c529f2 fix(scene3d): 深度缓冲初值 1.0->2.0 (NDC z in [-1,1], 初值须大于上界,否则远表面被永久剔平);撤掉 R/U/Y 阶段探针 2026-10-15 17:42:13 +08:00
TermiNexus 03dcd16f8b chore(debug): Scene3D 渲染线程加阶段探针(R/U/Y 每帧标记) - 定位冻结卡在 Render/update/yield 哪一步 2026-10-15 17:39:17 +08:00
TermiNexus 30620a2d0c chore(debug): Scene3D 临时探针打印 _time_val 位模式 - 区分时间退化与被内存写坏/几何深度剔除 2026-10-15 17:28:56 +08:00
TermiNexus abd13260af fix(scene3d): 时间相位回绕 4pi - 避免 float32 相位精度随运行退化致 SIN 波形塌平与热力图失色 2026-10-15 17:25:24 +08:00
TermiNexus 53535c557e fix(scene3d): Mat4_Identity/Mul/LookAt 改回值语义,修悬垂指针致投影矩阵损坏、fb 越界写砸坏 _winbufs 2026-10-15 16:09:15 +08:00
TermiNexus f42d8a5248 revert(HelloWorld): 回调恢复为 &_on_submit(编译器已支持对函数取址)
上一提交为绕过 CastError 曾改成直接传函数名;现编译器已修(ViperC 70c271d:取址分支
补 Ptr(Ptr(Func)) 分支),`&func` 会正确给出 Ptr(Func)(一级),故恢复原始写法。
2026-10-14 16:38:18 +08:00
TermiNexus 5da1e3f62a fix(HelloWorld): 回调改传函数名本身,去掉多余的 &(函数名已是地址)
vpui.Button(..., &_on_submit) 把函数地址又取了一层 → fn**(二级),与形参
callback: t.CPtr(一级 i8*)级数不符;新收紧的隐式转换规则下报 CastError:
  implicit pointer-to-pointer conversion is forbidden: pointer level differs
  (source level 2 -> target level 1);
  source: level 2, pointee !llvm.ptr -> target: level 1, pointee i8
改为直接传 _on_submit,与代码库既有写法一致(如 idt.irqInstallHandler(12, irq_handler, "mouse"))。
2026-10-14 16:31:24 +08:00
TermiNexus d093d3fc8b chore: 改名同步 TransPyV -> ViperC(源码/配置内的纯替换) 2026-10-12 15:06:50 +08:00
TermiNexus 5b4bab59cc chore(ViperOS): 合并落库内核侧在途改动并移除 vpsdk wiki 拷贝
VKernel / vpsdk / Apps / Libs 共 30 个源文件:内核与 SDK 侧的新语法适配及编译修正(含 bootinfo.vp / main.vp 位宽改 uint64、gfx.vp 前向引用改指针、devfs.vp 指针解引用赋值、elf.vp 跨模块函数取值等)。删除 vpsdk/wiki/*.md(14 文件,约 -8100 行):与仓库根 wiki 重复的拷贝,统一以根 wiki 为唯一来源。
2026-10-07 19:04:33 +08:00
TermiNexus 2a54e2bafb 清理了 t.CVoid 2026-09-16 16:07:04 +08:00