Compare commits
7
Commits
7a6be7f66e
..
64bit
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
e69b134bff | ||
|
|
a6a55153af | ||
|
|
e462165049 | ||
|
|
b71e6d67b4 | ||
|
|
465cf1deca | ||
|
|
f8911ccdec | ||
|
|
a27d9cb39d |
No files matched your search
+10
-10
@@ -22,12 +22,12 @@ type
|
|||||||
THeapPageHeader = memory.heap.THeapPageHeader;
|
THeapPageHeader = memory.heap.THeapPageHeader;
|
||||||
|
|
||||||
procedure init;
|
procedure init;
|
||||||
function kalloc(size : uint32) : void;
|
function kalloc(size : SizeUInt) : void;
|
||||||
function klalloc(size : uint32) : void;
|
function klalloc(size : SizeUInt) : void;
|
||||||
procedure klfree(address : uint32);
|
procedure klfree(address : PtrUInt);
|
||||||
function kpalloc(address : uint32) : void;
|
function kpalloc(address : PtrUInt) : void;
|
||||||
procedure kfree(area : void);
|
procedure kfree(area : void);
|
||||||
function lmm_total_free : uint32;
|
function lmm_total_free : SizeUInt;
|
||||||
function lmm_page_count : uint32;
|
function lmm_page_count : uint32;
|
||||||
|
|
||||||
implementation
|
implementation
|
||||||
@@ -37,22 +37,22 @@ begin
|
|||||||
memory.heap.init;
|
memory.heap.init;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function kalloc(size : uint32) : void; inline;
|
function kalloc(size : SizeUInt) : void; inline;
|
||||||
begin
|
begin
|
||||||
kalloc := memory.heap.kalloc(size);
|
kalloc := memory.heap.kalloc(size);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function klalloc(size : uint32) : void; inline;
|
function klalloc(size : SizeUInt) : void; inline;
|
||||||
begin
|
begin
|
||||||
klalloc := memory.heap.klalloc(size);
|
klalloc := memory.heap.klalloc(size);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure klfree(address : uint32); inline;
|
procedure klfree(address : PtrUInt); inline;
|
||||||
begin
|
begin
|
||||||
memory.heap.klfree(address);
|
memory.heap.klfree(address);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function kpalloc(address : uint32) : void; inline;
|
function kpalloc(address : PtrUInt) : void; inline;
|
||||||
begin
|
begin
|
||||||
kpalloc := memory.heap.kpalloc(address);
|
kpalloc := memory.heap.kpalloc(address);
|
||||||
end;
|
end;
|
||||||
@@ -62,7 +62,7 @@ begin
|
|||||||
memory.heap.kfree(area);
|
memory.heap.kfree(area);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function lmm_total_free : uint32; inline;
|
function lmm_total_free : SizeUInt; inline;
|
||||||
begin
|
begin
|
||||||
lmm_total_free := memory.heap.lmm_total_free;
|
lmm_total_free := memory.heap.lmm_total_free;
|
||||||
end;
|
end;
|
||||||
|
|||||||
@@ -205,7 +205,7 @@ Key constants:
|
|||||||
- `DATA_OFFSET = $10000` — data area starts at 64 KB into each page
|
- `DATA_OFFSET = $10000` — data area starts at 64 KB into each page
|
||||||
- `LARGE_ALLOC_MAGIC = $FFFFFFFE` — sentinel for klalloc'd multi-page allocations
|
- `LARGE_ALLOC_MAGIC = $FFFFFFFE` — sentinel for klalloc'd multi-page allocations
|
||||||
|
|
||||||
Interrupt safety: `pushfd; cli; pop saved_flags` (stack-balanced) + `restore_if(saved_flags)`
|
Interrupt safety: `pushfd; cli; pop saved_flags` (stack-balanced) + `arch.platform.cpu.unlock(saved_flags)`
|
||||||
inline procedure that only restores IF via `sti`, avoiding dangerous EFLAGS restoration
|
inline procedure that only restores IF via `sti`, avoiding dangerous EFLAGS restoration
|
||||||
(IOPL, NT, VM, AC bits that caused Bad-TSS on IRET).
|
(IOPL, NT, VM, AC bits that caused Bad-TSS on IRET).
|
||||||
|
|
||||||
@@ -256,7 +256,7 @@ list, fixes Search_Page, calls `free_page_at_address`). Skips Root_Page.
|
|||||||
|
|
||||||
| Bug | Root Cause | Fix |
|
| Bug | Root Cause | Fix |
|
||||||
|-----|-----------|-----|
|
|-----|-----------|-----|
|
||||||
| Bad TSS exception during network processing | `pushfd`/`popfd` across separate asm blocks: FPC doesn't track ESP changes in asm, causing EFLAGS corruption (NT=1, IOPL wrong) → Bad TSS on IRET | Stack-balanced `pushfd; cli; pop local_var` + `restore_if()` that only does `sti` if IF was set |
|
| Bad TSS exception during network processing | `pushfd`/`popfd` across separate asm blocks: FPC doesn't track ESP changes in asm, causing EFLAGS corruption (NT=1, IOPL wrong) → Bad TSS on IRET | Stack-balanced `pushfd; cli; pop local_var` + `arch.platform.cpu.unlock()` that only does `sti` if IF was set |
|
||||||
| GPF from SSE MOVAPS in doublebuffer flush | `SIZE_PREFIX=4`→8 gave 8-byte alignment; `MOVAPS` needs 16-byte. `klalloc` returned `page+8` (not 16-aligned) | `SIZE_PREFIX=16` (4B size + 12B pad), klalloc header expanded to 16 bytes |
|
| GPF from SSE MOVAPS in doublebuffer flush | `SIZE_PREFIX=4`→8 gave 8-byte alignment; `MOVAPS` needs 16-byte. `klalloc` returned `page+8` (not 16-aligned) | `SIZE_PREFIX=16` (4B size + 12B pad), klalloc header expanded to 16 bytes |
|
||||||
| Pages never freed (historic) | `free_page` extracted wrong block index from PDE Address field | Fixed extraction to `Address SHR 10` — page freeing works for the first time |
|
| Pages never freed (historic) | `free_page` extracted wrong block index from PDE Address field | Fixed extraction to `Address SHR 10` — page freeing works for the first time |
|
||||||
|
|
||||||
|
|||||||
+218
-8
File diff suppressed because it is too large.
Load diff
@@ -19,7 +19,7 @@ Every allocation is preceded by a 16-byte prefix: 4 bytes for the unit count, 12
|
|||||||
|
|
||||||
Allocations larger than a single heap page's capacity are handled by `klalloc`, which maps contiguous virtual pages and stores a magic sentinel (`$FFFFFFFE`) in the header so `kfree` can identify them and call `klfree` instead of the normal bitmap path.
|
Allocations larger than a single heap page's capacity are handled by `klalloc`, which maps contiguous virtual pages and stores a magic sentinel (`$FFFFFFFE`) in the header so `kfree` can identify them and call `klfree` instead of the normal bitmap path.
|
||||||
|
|
||||||
`kalloc` and `kfree` disable interrupts for the duration of their critical sections using a stack-balanced `pushfd`/`cli`/`pop` sequence and restore the interrupt flag via `restore_if` on all exit paths.
|
`kalloc` and `kfree` disable interrupts for the duration of their critical sections using a stack-balanced `pushfd`/`cli`/`pop` sequence and restore the interrupt flag via `arch.platform.cpu.unlock` on all exit paths.
|
||||||
|
|
||||||
## Dependencies
|
## Dependencies
|
||||||
|
|
||||||
@@ -132,7 +132,7 @@ Returns the number of heap pages currently in the linked list.
|
|||||||
|
|
||||||
## Notes
|
## Notes
|
||||||
|
|
||||||
The `restore_if` helper checks bit 9 (IF) of the saved EFLAGS word and issues `STI` only if interrupts were enabled on entry. It uses `STI` rather than `POPFD` to avoid restoring potentially dangerous EFLAGS bits (IOPL, NT, VM, AC) that could trigger a General Protection Fault or Bad-TSS on the next `IRET`.
|
The `arch.platform.cpu.unlock` helper checks bit 9 (IF) of the saved EFLAGS word and issues `STI` only if interrupts were enabled on entry. It uses `STI` rather than `POPFD` to avoid restoring potentially dangerous EFLAGS bits (IOPL, NT, VM, AC) that could trigger a General Protection Fault or Bad-TSS on the next `IRET`.
|
||||||
|
|
||||||
When `DEBUG_LMM` is defined, `kalloc` allocates one additional unit and writes `GUARD_MAGIC` at the end of the allocation. `kfree` verifies this sentinel before freeing; a mismatch triggers a GPF with a syslog error, catching buffer overruns at free time.
|
When `DEBUG_LMM` is defined, `kalloc` allocates one additional unit and writes `GUARD_MAGIC` at the end of the allocation. `kfree` verifies this sentinel before freeing; a mismatch triggers a GPF with a syslog error, catching buffer overruns at free time.
|
||||||
|
|
||||||
|
|||||||
@@ -22,7 +22,7 @@ unit app.base64;
|
|||||||
interface
|
interface
|
||||||
|
|
||||||
uses
|
uses
|
||||||
io.stdio, core.util, arch.x86.util, core.strings, debug.tracer, core.enc.base64, memory.heap;
|
io.stdio, core.util, arch.platform.cpu, core.strings, debug.tracer, core.enc.base64, memory.heap;
|
||||||
|
|
||||||
procedure init();
|
procedure init();
|
||||||
|
|
||||||
|
|||||||
@@ -22,7 +22,7 @@ unit app.dhclient;
|
|||||||
interface
|
interface
|
||||||
|
|
||||||
uses
|
uses
|
||||||
io.stdio, core.util, arch.x86.util, core.strings, debug.tracer, driver.net.proto.dhcp;
|
io.stdio, core.util, arch.platform.cpu, core.strings, debug.tracer, driver.net.proto.dhcp;
|
||||||
|
|
||||||
procedure init();
|
procedure init();
|
||||||
|
|
||||||
|
|||||||
@@ -25,7 +25,7 @@ uses
|
|||||||
core.strings,
|
core.strings,
|
||||||
io.stdio,
|
io.stdio,
|
||||||
debug.tracer,
|
debug.tracer,
|
||||||
core.util, arch.x86.util,
|
core.util, arch.platform.cpu,
|
||||||
driver.storage.vol.mgr;
|
driver.storage.vol.mgr;
|
||||||
|
|
||||||
var
|
var
|
||||||
@@ -254,7 +254,7 @@ begin
|
|||||||
{ Allocate a zero buffer - 64 sectors at a time }
|
{ Allocate a zero buffer - 64 sectors at a time }
|
||||||
bufSects := 64;
|
bufSects := 64;
|
||||||
buf := puint32(kalloc(bufSects * device^.sectorSize));
|
buf := puint32(kalloc(bufSects * device^.sectorSize));
|
||||||
memset(uint32(buf), 0, bufSects * device^.sectorSize);
|
memset(PtrUInt(buf), 0, bufSects * device^.sectorSize);
|
||||||
|
|
||||||
print('Wiping device ');
|
print('Wiping device ');
|
||||||
printint(idx);
|
printint(idx);
|
||||||
|
|||||||
+12
-11
@@ -34,7 +34,7 @@ uses
|
|||||||
driver.video,
|
driver.video,
|
||||||
driver.storage.vol.mgr,
|
driver.storage.vol.mgr,
|
||||||
driver.video.windows,
|
driver.video.windows,
|
||||||
core.util, arch.x86.util;
|
core.util, arch.platform.cpu;
|
||||||
|
|
||||||
const
|
const
|
||||||
WIN_W = 740;
|
WIN_W = 740;
|
||||||
@@ -129,9 +129,9 @@ begin
|
|||||||
item := PUIText(kalloc(sizeof(TUIText)+n+m+1));
|
item := PUIText(kalloc(sizeof(TUIText)+n+m+1));
|
||||||
if item = nil then exit;
|
if item = nil then exit;
|
||||||
item^.Next := TextTemps; TextTemps := item;
|
item^.Next := TextTemps; TextTemps := item;
|
||||||
dest := pchar(uint32(item)+sizeof(TUIText));
|
dest := pchar(PtrUInt(item)+sizeof(TUIText));
|
||||||
if n > 0 then memcpy(uint32(a), uint32(dest), n);
|
if n > 0 then memcpy(PtrUInt(a), PtrUInt(dest), n);
|
||||||
if m > 0 then memcpy(uint32(b), uint32(dest)+n, m);
|
if m > 0 then memcpy(PtrUInt(b), PtrUInt(dest)+n, m);
|
||||||
dest[n+m] := #0; uiConcat := dest;
|
dest[n+m] := #0; uiConcat := dest;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@@ -606,7 +606,7 @@ begin
|
|||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
memset(uint32(@part), 0, sizeof(TPartition_table));
|
memset(PtrUInt(@part), 0, sizeof(TPartition_table));
|
||||||
driver.storage.vol.mbr.setup_partition(@part, lba, sectors);
|
driver.storage.vol.mbr.setup_partition(@part, lba, sectors);
|
||||||
cbCtx := begin_partition_ui(1);
|
cbCtx := begin_partition_ui(1);
|
||||||
if cbCtx = nil then exit;
|
if cbCtx = nil then exit;
|
||||||
@@ -702,18 +702,19 @@ end;
|
|||||||
procedure operation_done(error : TError; userdata : pointer);
|
procedure operation_done(error : TError; userdata : pointer);
|
||||||
var
|
var
|
||||||
ctx : PFmtUICallbackCtx;
|
ctx : PFmtUICallbackCtx;
|
||||||
flags : uint32;
|
flags : PtrUInt;
|
||||||
begin
|
begin
|
||||||
ctx := PFmtUICallbackCtx(userdata);
|
ctx := PFmtUICallbackCtx(userdata);
|
||||||
if ctx <> nil then begin
|
if ctx <> nil then begin
|
||||||
asm pushfd; cli; pop flags end;
|
flags := arch.platform.cpu.lock;
|
||||||
if ctx^.SessionID = ui_session_id then begin
|
if ctx^.SessionID = ui_session_id then begin
|
||||||
fmt_done_error := error;
|
fmt_done_error := error;
|
||||||
fmt_done_vol_idx := ctx^.VolumeIdx;
|
fmt_done_vol_idx := ctx^.VolumeIdx;
|
||||||
done_kind := ctx^.Kind; done_device := ctx^.DeviceIdx;
|
done_kind := ctx^.Kind;
|
||||||
|
done_device := ctx^.DeviceIdx;
|
||||||
puint32(@fmt_done_flag)^ := 1;
|
puint32(@fmt_done_flag)^ := 1;
|
||||||
end;
|
end;
|
||||||
if (flags and $200) <> 0 then asm sti end;
|
arch.platform.cpu.unlock(flags);
|
||||||
kfree(void(ctx));
|
kfree(void(ctx));
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
@@ -824,7 +825,7 @@ begin
|
|||||||
fs := driver.storage.fs.mgr.get_filesystem(selIdx);
|
fs := driver.storage.fs.mgr.get_filesystem(selIdx);
|
||||||
if fs = nil then begin closeMsgBox; exit; end;
|
if fs = nil then begin closeMsgBox; exit; end;
|
||||||
|
|
||||||
memset(uint32(@params), 0, sizeof(TFSFormatParams));
|
memset(PtrUInt(@params), 0, sizeof(TFSFormatParams));
|
||||||
params.Version := FS_FORMAT_PARAMS_VERSION_1;
|
params.Version := FS_FORMAT_PARAMS_VERSION_1;
|
||||||
paramPtr := nil;
|
paramPtr := nil;
|
||||||
|
|
||||||
@@ -874,7 +875,7 @@ begin
|
|||||||
if fs^.validateLabelCallback(text,normalized) <> eNone then begin
|
if fs^.validateLabelCallback(text,normalized) <> eNone then begin
|
||||||
set_fmt_param_error('Use up to 11 ASCII characters without punctuation such as / or :'); exit;
|
set_fmt_param_error('Use up to 11 ASCII characters without punctuation such as / or :'); exit;
|
||||||
end;
|
end;
|
||||||
memcpy(uint32(@normalized[0]),uint32(@params.LabelText[0]),12);
|
memcpy(PtrUInt(@normalized[0]),PtrUInt(@params.LabelText[0]),12);
|
||||||
params.Flags := params.Flags or FS_FORMAT_PARAM_LABEL; paramPtr := @params;
|
params.Flags := params.Flags or FS_FORMAT_PARAM_LABEL; paramPtr := @params;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
|||||||
@@ -32,7 +32,7 @@ uses
|
|||||||
core.gfx.fileicons,
|
core.gfx.fileicons,
|
||||||
debug.tracer,
|
debug.tracer,
|
||||||
core.util,
|
core.util,
|
||||||
arch.x86.util;
|
arch.platform.cpu;
|
||||||
|
|
||||||
const
|
const
|
||||||
WIN_W = 800;
|
WIN_W = 800;
|
||||||
@@ -785,9 +785,9 @@ begin
|
|||||||
dir_names := PNameBuf(kalloc(sizeof(TNameBuf)));
|
dir_names := PNameBuf(kalloc(sizeof(TNameBuf)));
|
||||||
file_names := PNameBuf(kalloc(sizeof(TNameBuf)));
|
file_names := PNameBuf(kalloc(sizeof(TNameBuf)));
|
||||||
file_sizes := PSizeBuf(kalloc(sizeof(TSizeBuf)));
|
file_sizes := PSizeBuf(kalloc(sizeof(TSizeBuf)));
|
||||||
memset(uint32(dir_names), 0, sizeof(TNameBuf));
|
memset(PtrUInt(dir_names), 0, sizeof(TNameBuf));
|
||||||
memset(uint32(file_names), 0, sizeof(TNameBuf));
|
memset(PtrUInt(file_names), 0, sizeof(TNameBuf));
|
||||||
memset(uint32(file_sizes), 0, sizeof(TSizeBuf));
|
memset(PtrUInt(file_sizes), 0, sizeof(TSizeBuf));
|
||||||
|
|
||||||
{ Load directory from VFS — this may do disk I/O }
|
{ Load directory from VFS — this may do disk I/O }
|
||||||
Map := driver.storage.vfs.GetDirectoryListingFrom(state^.cur_path, '/');
|
Map := driver.storage.vfs.GetDirectoryListingFrom(state^.cur_path, '/');
|
||||||
@@ -1330,7 +1330,7 @@ begin
|
|||||||
parent := stringCopy('/')
|
parent := stringCopy('/')
|
||||||
else begin
|
else begin
|
||||||
parent := pchar(kalloc(uint32(i) + 1));
|
parent := pchar(kalloc(uint32(i) + 1));
|
||||||
memcpy(uint32(cur), uint32(parent), uint32(i));
|
memcpy(PtrUInt(cur), PtrUInt(parent), uint32(i));
|
||||||
parent[i] := char(0);
|
parent[i] := char(0);
|
||||||
end;
|
end;
|
||||||
navigate_to(state, parent);
|
navigate_to(state, parent);
|
||||||
@@ -1440,7 +1440,7 @@ begin
|
|||||||
|
|
||||||
{ Segment name label }
|
{ Segment name label }
|
||||||
segBuf := pchar(kalloc(segEnd - segStart + 1));
|
segBuf := pchar(kalloc(segEnd - segStart + 1));
|
||||||
memcpy(uint32(@path[segStart]), uint32(segBuf), segEnd - segStart);
|
memcpy(PtrUInt(@path[segStart]), uint32(segBuf), segEnd - segStart);
|
||||||
segBuf[segEnd - segStart] := char(0);
|
segBuf[segEnd - segStart] := char(0);
|
||||||
lbl := lv_label_create(btn);
|
lbl := lv_label_create(btn);
|
||||||
lv_label_set_text(lbl, segBuf);
|
lv_label_set_text(lbl, segBuf);
|
||||||
@@ -1979,7 +1979,7 @@ begin
|
|||||||
if state^.tabs[idx] <> nil then
|
if state^.tabs[idx] <> nil then
|
||||||
free_tab_snapshot(state^.tabs[idx]);
|
free_tab_snapshot(state^.tabs[idx]);
|
||||||
snap := PTabSnapshot(kalloc(sizeof(TTabSnapshot)));
|
snap := PTabSnapshot(kalloc(sizeof(TTabSnapshot)));
|
||||||
memset(uint32(snap), 0, sizeof(TTabSnapshot));
|
memset(PtrUInt(snap), 0, sizeof(TTabSnapshot));
|
||||||
if state^.cur_path <> nil then
|
if state^.cur_path <> nil then
|
||||||
snap^.cur_path := stringCopy(state^.cur_path)
|
snap^.cur_path := stringCopy(state^.cur_path)
|
||||||
else
|
else
|
||||||
@@ -2090,7 +2090,7 @@ begin
|
|||||||
save_tab(state, state^.active_tab);
|
save_tab(state, state^.active_tab);
|
||||||
{ Create snapshot for new tab }
|
{ Create snapshot for new tab }
|
||||||
snap := PTabSnapshot(kalloc(sizeof(TTabSnapshot)));
|
snap := PTabSnapshot(kalloc(sizeof(TTabSnapshot)));
|
||||||
memset(uint32(snap), 0, sizeof(TTabSnapshot));
|
memset(PtrUInt(snap), 0, sizeof(TTabSnapshot));
|
||||||
snap^.cur_path := stringCopy(path);
|
snap^.cur_path := stringCopy(path);
|
||||||
snap^.hist_len := 0;
|
snap^.hist_len := 0;
|
||||||
snap^.hist_pos := 0;
|
snap^.hist_pos := 0;
|
||||||
@@ -3053,7 +3053,7 @@ begin
|
|||||||
|
|
||||||
{ Allocate and zero-initialise state }
|
{ Allocate and zero-initialise state }
|
||||||
state := PFileBrowserState(kalloc(sizeof(TFileBrowserState)));
|
state := PFileBrowserState(kalloc(sizeof(TFileBrowserState)));
|
||||||
memset(uint32(state), 0, sizeof(TFileBrowserState));
|
memset(PtrUInt(state), 0, sizeof(TFileBrowserState));
|
||||||
state^.win_id := g_win_id;
|
state^.win_id := g_win_id;
|
||||||
state^.cur_path := stringCopy('/');
|
state^.cur_path := stringCopy('/');
|
||||||
state^.view_mode := vmDetail;
|
state^.view_mode := vmDetail;
|
||||||
|
|||||||
@@ -64,7 +64,7 @@ uses
|
|||||||
core.strings.helpers,
|
core.strings.helpers,
|
||||||
io.syslog,
|
io.syslog,
|
||||||
debug.tracer,
|
debug.tracer,
|
||||||
core.util, arch.x86.util,
|
core.util, arch.platform.cpu,
|
||||||
driver.storage.vfs;
|
driver.storage.vfs;
|
||||||
|
|
||||||
const
|
const
|
||||||
@@ -325,9 +325,9 @@ begin
|
|||||||
dir_names := PNameBuf(kalloc(sizeof(TNameBuf)));
|
dir_names := PNameBuf(kalloc(sizeof(TNameBuf)));
|
||||||
file_names := PNameBuf(kalloc(sizeof(TNameBuf)));
|
file_names := PNameBuf(kalloc(sizeof(TNameBuf)));
|
||||||
file_sizes := PSizeBuf(kalloc(sizeof(TSizeBuf)));
|
file_sizes := PSizeBuf(kalloc(sizeof(TSizeBuf)));
|
||||||
memset(uint32(dir_names), 0, sizeof(TNameBuf));
|
memset(PtrUInt(dir_names), 0, sizeof(TNameBuf));
|
||||||
memset(uint32(file_names), 0, sizeof(TNameBuf));
|
memset(PtrUInt(file_names), 0, sizeof(TNameBuf));
|
||||||
memset(uint32(file_sizes), 0, sizeof(TSizeBuf));
|
memset(PtrUInt(file_sizes), 0, sizeof(TSizeBuf));
|
||||||
|
|
||||||
{ Sync path bar }
|
{ Sync path bar }
|
||||||
if p^.path_bar <> nil then
|
if p^.path_bar <> nil then
|
||||||
@@ -898,7 +898,7 @@ begin
|
|||||||
io.syslog.logln('FPCIK', 'make_picker: enter');
|
io.syslog.logln('FPCIK', 'make_picker: enter');
|
||||||
|
|
||||||
p := PPicker(kalloc(sizeof(TPicker)));
|
p := PPicker(kalloc(sizeof(TPicker)));
|
||||||
memset(uint32(p), 0, sizeof(TPicker));
|
memset(PtrUInt(p), 0, sizeof(TPicker));
|
||||||
p^.cb := cb;
|
p^.cb := cb;
|
||||||
p^.userdata := userdata;
|
p^.userdata := userdata;
|
||||||
p^.is_save := is_save;
|
p^.is_save := is_save;
|
||||||
|
|||||||
@@ -22,7 +22,7 @@ unit app.md5sum;
|
|||||||
interface
|
interface
|
||||||
|
|
||||||
uses
|
uses
|
||||||
io.stdio, core.util, arch.x86.util, core.strings, debug.tracer, core.enc.md5;
|
memory.heap, io.stdio, core.util, arch.platform.cpu, core.strings, debug.tracer, core.enc.md5;
|
||||||
|
|
||||||
procedure init();
|
procedure init();
|
||||||
|
|
||||||
@@ -36,6 +36,10 @@ var
|
|||||||
i : uint32;
|
i : uint32;
|
||||||
|
|
||||||
begin
|
begin
|
||||||
|
if paramCount(Params) = 0 then begin
|
||||||
|
io.stdio.bufWriteStrLn(stderr_buf, 'Usage: MD5SUM <word>');
|
||||||
|
exit;
|
||||||
|
end;
|
||||||
md5word:= getParam(0, Params);
|
md5word:= getParam(0, Params);
|
||||||
wordlen:= stringSize(md5word);
|
wordlen:= stringSize(md5word);
|
||||||
MD5_Hash := MD5Buffer(puint8(md5word), wordlen);
|
MD5_Hash := MD5Buffer(puint8(md5word), wordlen);
|
||||||
@@ -43,6 +47,7 @@ begin
|
|||||||
io.stdio.bufWriteHexPair(stdout_buf, MD5_Hash^[i]);
|
io.stdio.bufWriteHexPair(stdout_buf, MD5_Hash^[i]);
|
||||||
end;
|
end;
|
||||||
io.stdio.bufWriteStrLn(stdout_buf, ' ');
|
io.stdio.bufWriteStrLn(stdout_buf, ' ');
|
||||||
|
memory.heap.kfree(void(MD5_Hash));
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure init();
|
procedure init();
|
||||||
|
|||||||
+20
-40
@@ -22,7 +22,7 @@ unit app.meminfo;
|
|||||||
interface
|
interface
|
||||||
|
|
||||||
uses
|
uses
|
||||||
io.stdio, arch.x86.multiboot, arch.x86.memory.physical, memory.heap, debug.tracer;
|
io.stdio, arch.platform.memory, memory.heap, debug.tracer;
|
||||||
|
|
||||||
procedure init();
|
procedure init();
|
||||||
|
|
||||||
@@ -30,50 +30,30 @@ implementation
|
|||||||
|
|
||||||
procedure run(Params : PParamList; stdin_buf, stdout_buf, stderr_buf : POutBuf);
|
procedure run(Params : PParamList; stdin_buf, stdout_buf, stderr_buf : POutBuf);
|
||||||
var
|
var
|
||||||
pmm_total, pmm_free, pmm_used : uint32;
|
total, available: uint64;
|
||||||
lmm_pages, lmm_free : uint32;
|
heapPages: uint32;
|
||||||
begin
|
begin
|
||||||
{ Multiboot memory info }
|
total := arch.platform.memory.totalPhysicalBytes;
|
||||||
io.stdio.bufWriteStrLn(stdout_buf, '--- Multiboot ---');
|
available := arch.platform.memory.freePhysicalBytes;
|
||||||
io.stdio.bufWriteStr(stdout_buf, 'Lower Memory : ');
|
io.stdio.bufWriteStr(stdout_buf, 'Usable Physical: ');
|
||||||
io.stdio.bufWriteInt(stdout_buf, multibootinfo^.mem_lower);
|
io.stdio.bufWriteInt(stdout_buf, total div 1024);
|
||||||
io.stdio.bufWriteStrLn(stdout_buf, ' KB');
|
io.stdio.bufWriteStrLn(stdout_buf, ' KiB');
|
||||||
io.stdio.bufWriteStr(stdout_buf, 'Upper Memory : ');
|
|
||||||
io.stdio.bufWriteInt(stdout_buf, multibootinfo^.mem_upper);
|
|
||||||
io.stdio.bufWriteStrLn(stdout_buf, ' KB');
|
|
||||||
io.stdio.bufWriteStr(stdout_buf, 'Total Memory : ');
|
|
||||||
io.stdio.bufWriteInt(stdout_buf, ((multibootinfo^.mem_upper + 1000) div 1024) + 1);
|
|
||||||
io.stdio.bufWriteStrLn(stdout_buf, ' MB');
|
|
||||||
|
|
||||||
{ PMM stats }
|
|
||||||
io.stdio.bufWriteStrLn(stdout_buf, '--- PMM (4 MB blocks) ---');
|
|
||||||
pmm_total := arch.x86.memory.physical.pmm_total_blocks;
|
|
||||||
pmm_free := arch.x86.memory.physical.pmm_free_blocks;
|
|
||||||
pmm_used := pmm_total - pmm_free;
|
|
||||||
io.stdio.bufWriteStr(stdout_buf, 'Total Blocks : ');
|
|
||||||
io.stdio.bufWriteIntLn(stdout_buf, pmm_total);
|
|
||||||
io.stdio.bufWriteStr(stdout_buf, 'Free Blocks : ');
|
|
||||||
io.stdio.bufWriteIntLn(stdout_buf, pmm_free);
|
|
||||||
io.stdio.bufWriteStr(stdout_buf, 'Used Blocks : ');
|
|
||||||
io.stdio.bufWriteIntLn(stdout_buf, pmm_used);
|
|
||||||
io.stdio.bufWriteStr(stdout_buf, 'Free Physical : ');
|
io.stdio.bufWriteStr(stdout_buf, 'Free Physical : ');
|
||||||
io.stdio.bufWriteInt(stdout_buf, pmm_free * 4);
|
io.stdio.bufWriteInt(stdout_buf, available div 1024);
|
||||||
io.stdio.bufWriteStrLn(stdout_buf, ' MB');
|
io.stdio.bufWriteStrLn(stdout_buf, ' KiB');
|
||||||
|
io.stdio.bufWriteStr(stdout_buf, 'Used Physical : ');
|
||||||
{ LMM heap stats }
|
io.stdio.bufWriteInt(stdout_buf, (total - available) div 1024);
|
||||||
io.stdio.bufWriteStrLn(stdout_buf, '--- LMM (Heap) ---');
|
io.stdio.bufWriteStrLn(stdout_buf, ' KiB');
|
||||||
lmm_pages := memory.heap.lmm_page_count;
|
heapPages := memory.heap.lmm_page_count;
|
||||||
lmm_free := memory.heap.lmm_total_free;
|
io.stdio.bufWriteStr(stdout_buf, 'Heap Regions : ');
|
||||||
io.stdio.bufWriteStr(stdout_buf, 'Heap Pages : ');
|
io.stdio.bufWriteIntLn(stdout_buf, heapPages);
|
||||||
io.stdio.bufWriteIntLn(stdout_buf, lmm_pages);
|
|
||||||
io.stdio.bufWriteStr(stdout_buf, 'Heap Size : ');
|
io.stdio.bufWriteStr(stdout_buf, 'Heap Size : ');
|
||||||
io.stdio.bufWriteInt(stdout_buf, lmm_pages * 4);
|
io.stdio.bufWriteInt(stdout_buf, uint64(heapPages) * PAGE_SIZE_LMM div 1024);
|
||||||
io.stdio.bufWriteStrLn(stdout_buf, ' MB');
|
io.stdio.bufWriteStrLn(stdout_buf, ' KiB');
|
||||||
io.stdio.bufWriteStr(stdout_buf, 'Heap Free : ');
|
io.stdio.bufWriteStr(stdout_buf, 'Heap Free : ');
|
||||||
io.stdio.bufWriteInt(stdout_buf, lmm_free div 1024);
|
io.stdio.bufWriteInt(stdout_buf, memory.heap.lmm_total_free div 1024);
|
||||||
io.stdio.bufWriteStrLn(stdout_buf, ' KB');
|
io.stdio.bufWriteStrLn(stdout_buf, ' KiB');
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure init();
|
procedure init();
|
||||||
begin
|
begin
|
||||||
debug.tracer.push_trace('meminfo.init');
|
debug.tracer.push_trace('meminfo.init');
|
||||||
|
|||||||
+1
-17
@@ -23,10 +23,9 @@ unit app.mgr;
|
|||||||
interface
|
interface
|
||||||
|
|
||||||
uses
|
uses
|
||||||
boot.mgr,
|
|
||||||
debug.tracer, io.stdio, proc.mgr,
|
debug.tracer, io.stdio, proc.mgr,
|
||||||
//progs
|
//progs
|
||||||
app.base64, app.md5sum, app.dhclient, app.vbeinfo, app.testcmd, app.ping, app.meminfo, app.setres, app.iotest,
|
app.base64, app.md5sum, app.dhclient, app.testcmd, app.ping, app.meminfo, app.setres,
|
||||||
//drivers
|
//drivers
|
||||||
driver.storage.ctl.ram, driver.mgr,
|
driver.storage.ctl.ram, driver.mgr,
|
||||||
//network
|
//network
|
||||||
@@ -35,8 +34,6 @@ uses
|
|||||||
driver.storage.filedispatch,
|
driver.storage.filedispatch,
|
||||||
//wasm
|
//wasm
|
||||||
app.wasm.runner,
|
app.wasm.runner,
|
||||||
app.divzero,
|
|
||||||
app.bsod,
|
|
||||||
app.vterminal;
|
app.vterminal;
|
||||||
|
|
||||||
{ Initialize all baked-in programs }
|
{ Initialize all baked-in programs }
|
||||||
@@ -47,7 +44,6 @@ implementation
|
|||||||
uses
|
uses
|
||||||
core.version,
|
core.version,
|
||||||
//command provider units
|
//command provider units
|
||||||
arch.x86.cpu,
|
|
||||||
app.diskcmd, driver.bus.usb.core, app.diskutil, app.notepad, app.partcmd, app.volcmd,
|
app.diskcmd, driver.bus.usb.core, app.diskutil, app.notepad, app.partcmd, app.volcmd,
|
||||||
app.filebrowser;
|
app.filebrowser;
|
||||||
|
|
||||||
@@ -56,16 +52,10 @@ begin
|
|||||||
debug.tracer.push_trace('app.mgr.init');
|
debug.tracer.push_trace('app.mgr.init');
|
||||||
|
|
||||||
{ Register commands from provider units }
|
{ Register commands from provider units }
|
||||||
io.stdio.registerCommand('CPU', @arch.x86.cpu.Terminal_Command_CPU, 'CPU Info.');
|
|
||||||
io.stdio.registerCommand('DEV', @driver.mgr.terminal_command_dev, 'Driver Management Interface.');
|
io.stdio.registerCommand('DEV', @driver.mgr.terminal_command_dev, 'Driver Management Interface.');
|
||||||
io.stdio.registerCommand('PS', @proc.mgr.terminal_command_ps, 'List running processes.');
|
io.stdio.registerCommand('PS', @proc.mgr.terminal_command_ps, 'List running processes.');
|
||||||
io.stdio.registerCommand('KILL', @proc.mgr.terminal_command_kill, 'Force-kill a process by PID.');
|
io.stdio.registerCommand('KILL', @proc.mgr.terminal_command_kill, 'Force-kill a process by PID.');
|
||||||
io.stdio.registerCommand('TERMINATE', @proc.mgr.terminal_command_terminate, 'Gracefully terminate a process by PID.');
|
io.stdio.registerCommand('TERMINATE', @proc.mgr.terminal_command_terminate, 'Gracefully terminate a process by PID.');
|
||||||
io.stdio.registerCommand('ARP', @driver.net.proto.arp.terminal_command_arp, 'Get ARP Table.');
|
|
||||||
io.stdio.registerCommand('IFCONFIG', @driver.net.proto.ipv4.terminal_command_ifconfig, 'Configure Network Settings.');
|
|
||||||
io.stdio.registerCommand('TCPCONNECT', @driver.net.proto.tcp.terminal_command_tcpconnect, 'Connect to a TCP host and send Hello World.');
|
|
||||||
io.stdio.registerCommand('TCPLISTEN', @driver.net.proto.tcp.terminal_command_tcplisten, 'Listen on a TCP port and log received data.');
|
|
||||||
io.stdio.registerCommand('TCPHTTP', @driver.net.proto.tcp.terminal_command_tcphttp, 'Send HTTP GET to a host IP (port 80 default).');
|
|
||||||
io.stdio.registerCommand('USB', @driver.bus.usb.core.terminal_command_usb, 'driver.bus.usb subsystem information.');
|
io.stdio.registerCommand('USB', @driver.bus.usb.core.terminal_command_usb, 'driver.bus.usb subsystem information.');
|
||||||
|
|
||||||
{ File dispatch — must init before apps that register handlers }
|
{ File dispatch — must init before apps that register handlers }
|
||||||
@@ -81,21 +71,15 @@ begin
|
|||||||
app.md5sum.init();
|
app.md5sum.init();
|
||||||
app.base64.init();
|
app.base64.init();
|
||||||
app.dhclient.init();
|
app.dhclient.init();
|
||||||
app.vbeinfo.init();
|
|
||||||
app.testcmd.init();
|
app.testcmd.init();
|
||||||
app.ping.init();
|
app.ping.init();
|
||||||
app.meminfo.init();
|
app.meminfo.init();
|
||||||
{ WASM & remaining apps }
|
{ WASM & remaining apps }
|
||||||
app.wasm.runner.init();
|
app.wasm.runner.init();
|
||||||
app.setres.init();
|
app.setres.init();
|
||||||
app.divzero.init();
|
|
||||||
app.bsod.init();
|
|
||||||
app.vterminal.init;
|
app.vterminal.init;
|
||||||
app.filebrowser.init();
|
app.filebrowser.init();
|
||||||
app.iotest.init();
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
Initialization
|
|
||||||
boot.mgr.registerBoot('app.mgr', @init, 'Program Manager', BOOT_MGR_BARRIER_LATE);
|
|
||||||
|
|
||||||
end.
|
end.
|
||||||
+14
-29
@@ -11,8 +11,7 @@
|
|||||||
- Status bar showing Line, Col, filename, and dirty flag
|
- Status bar showing Line, Col, filename, and dirty flag
|
||||||
|
|
||||||
Key design notes:
|
Key design notes:
|
||||||
- lv_event_t.stop_processing (bit 1 at struct byte offset 24) is set
|
- lv_event_stop_processing prevents LVGL's default textarea handler from also
|
||||||
directly to prevent LVGL's default textarea key handler from also
|
|
||||||
acting on keys we have fully handled ourselves.
|
acting on keys we have fully handled ourselves.
|
||||||
- Shift state is read from driver.hid.keyboard.is_shift / driver.hid.keyboard.is_ctrl.
|
- Shift state is read from driver.hid.keyboard.is_shift / driver.hid.keyboard.is_ctrl.
|
||||||
- selection anchor (sel_anchor) is stored as a sint32 byte offset;
|
- selection anchor (sel_anchor) is stored as a sint32 byte offset;
|
||||||
@@ -43,7 +42,7 @@ uses
|
|||||||
io.syslog,
|
io.syslog,
|
||||||
io.stdio,
|
io.stdio,
|
||||||
debug.tracer,
|
debug.tracer,
|
||||||
core.util, arch.x86.util,
|
core.util, arch.platform.cpu,
|
||||||
driver.storage.vfs,
|
driver.storage.vfs,
|
||||||
driver.video,
|
driver.video,
|
||||||
driver.video.windows;
|
driver.video.windows;
|
||||||
@@ -62,19 +61,6 @@ const
|
|||||||
|
|
||||||
FILE_BUF_SIZE = 65536; { 64 KB read / write buffer }
|
FILE_BUF_SIZE = 65536; { 64 KB read / write buffer }
|
||||||
|
|
||||||
{
|
|
||||||
Byte offset and bitmask for lv_event_t.stop_processing.
|
|
||||||
struct lv_event_t (32-bit ABI):
|
|
||||||
offset 0: current_target (ptr)
|
|
||||||
offset 4: original_target (ptr)
|
|
||||||
offset 8: code (uint32 — lv_event_code_t)
|
|
||||||
offset 12: user_data (ptr)
|
|
||||||
offset 16: param (ptr)
|
|
||||||
offset 20: prev (ptr)
|
|
||||||
offset 24: flags byte [bit0=deleted, bit1=stop_processing, bit2=stop_bubbling]
|
|
||||||
}
|
|
||||||
LV_EVT_STOP_OFF = 24;
|
|
||||||
LV_EVT_STOP_BIT = 2; { bit 1 = stop_processing }
|
|
||||||
|
|
||||||
type
|
type
|
||||||
PNotepadState = ^TNotepadState;
|
PNotepadState = ^TNotepadState;
|
||||||
@@ -130,8 +116,7 @@ procedure removeInstance(state: PNotepadState); forward;
|
|||||||
============================================================ }
|
============================================================ }
|
||||||
procedure stopEvent(e: Plv_event);
|
procedure stopEvent(e: Plv_event);
|
||||||
begin
|
begin
|
||||||
puint8(uint32(e) + LV_EVT_STOP_OFF)^ :=
|
lv_event_stop_processing(e);
|
||||||
puint8(uint32(e) + LV_EVT_STOP_OFF)^ or LV_EVT_STOP_BIT;
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ ============================================================
|
{ ============================================================
|
||||||
@@ -157,18 +142,18 @@ begin
|
|||||||
if to_idx < from_idx then to_idx := from_idx;
|
if to_idx < from_idx then to_idx := from_idx;
|
||||||
result_len := from_idx + ins_len + (src_len - to_idx);
|
result_len := from_idx + ins_len + (src_len - to_idx);
|
||||||
buf := pchar(kalloc(result_len + 1));
|
buf := pchar(kalloc(result_len + 1));
|
||||||
memset(uint32(buf), 0, result_len + 1);
|
memset(PtrUInt(buf), 0, result_len + 1);
|
||||||
pos := 0;
|
pos := 0;
|
||||||
if from_idx > 0 then begin
|
if from_idx > 0 then begin
|
||||||
memcpy(uint32(src), uint32(buf), from_idx);
|
memcpy(PtrUInt(src), PtrUInt(buf), from_idx);
|
||||||
pos := from_idx;
|
pos := from_idx;
|
||||||
end;
|
end;
|
||||||
if ins_len > 0 then begin
|
if ins_len > 0 then begin
|
||||||
memcpy(uint32(insert), uint32(@buf[pos]), ins_len);
|
memcpy(PtrUInt(insert), PtrUInt(@buf[pos]), ins_len);
|
||||||
pos := pos + ins_len;
|
pos := pos + ins_len;
|
||||||
end;
|
end;
|
||||||
if to_idx < src_len then
|
if to_idx < src_len then
|
||||||
memcpy(uint32(@src[to_idx]), uint32(@buf[pos]), src_len - to_idx);
|
memcpy(PtrUInt(@src[to_idx]), PtrUInt(@buf[pos]), src_len - to_idx);
|
||||||
buildSplicedString := buf;
|
buildSplicedString := buf;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@@ -198,12 +183,12 @@ begin
|
|||||||
|
|
||||||
{ Generous output buffer: original + 4 bytes per line (worst case ~512 lines) }
|
{ Generous output buffer: original + 4 bytes per line (worst case ~512 lines) }
|
||||||
out_buf := pchar(kalloc(src_len + 2049));
|
out_buf := pchar(kalloc(src_len + 2049));
|
||||||
memset(uint32(out_buf), 0, src_len + 2049);
|
memset(PtrUInt(out_buf), 0, src_len + 2049);
|
||||||
out_pos := 0;
|
out_pos := 0;
|
||||||
|
|
||||||
{ Copy everything before the affected region verbatim }
|
{ Copy everything before the affected region verbatim }
|
||||||
if first_ls > 0 then begin
|
if first_ls > 0 then begin
|
||||||
memcpy(uint32(src), uint32(out_buf), first_ls);
|
memcpy(PtrUInt(src), PtrUInt(out_buf), first_ls);
|
||||||
out_pos := first_ls;
|
out_pos := first_ls;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@@ -215,7 +200,7 @@ begin
|
|||||||
if i >= sel_end then begin
|
if i >= sel_end then begin
|
||||||
{ Past the affected region: copy the remainder verbatim }
|
{ Past the affected region: copy the remainder verbatim }
|
||||||
if i < src_len then begin
|
if i < src_len then begin
|
||||||
memcpy(uint32(@src[i]), uint32(@out_buf[out_pos]), src_len - i);
|
memcpy(PtrUInt(@src[i]), PtrUInt(@out_buf[out_pos]), src_len - i);
|
||||||
out_pos := out_pos + (src_len - i);
|
out_pos := out_pos + (src_len - i);
|
||||||
end;
|
end;
|
||||||
break;
|
break;
|
||||||
@@ -426,8 +411,8 @@ begin
|
|||||||
len := stringSize(txt);
|
len := stringSize(txt);
|
||||||
if len > FILE_BUF_SIZE - 1 then len := FILE_BUF_SIZE - 1;
|
if len > FILE_BUF_SIZE - 1 then len := FILE_BUF_SIZE - 1;
|
||||||
buf := pchar(kalloc(FILE_BUF_SIZE));
|
buf := pchar(kalloc(FILE_BUF_SIZE));
|
||||||
memset(uint32(buf), 0, FILE_BUF_SIZE);
|
memset(PtrUInt(buf), 0, FILE_BUF_SIZE);
|
||||||
memcpy(uint32(txt), uint32(buf), len);
|
memcpy(PtrUInt(txt), PtrUInt(buf), len);
|
||||||
fHandle := driver.storage.vfs.OpenFile(state^.currentPath, omReadWrite, @fError);
|
fHandle := driver.storage.vfs.OpenFile(state^.currentPath, omReadWrite, @fError);
|
||||||
if fHandle = 0 then
|
if fHandle = 0 then
|
||||||
fHandle := driver.storage.vfs.OpenFile(state^.currentPath, omCreate, @fError);
|
fHandle := driver.storage.vfs.OpenFile(state^.currentPath, omCreate, @fError);
|
||||||
@@ -477,7 +462,7 @@ begin
|
|||||||
exit;
|
exit;
|
||||||
end;
|
end;
|
||||||
buf := pchar(kalloc(FILE_BUF_SIZE));
|
buf := pchar(kalloc(FILE_BUF_SIZE));
|
||||||
memset(uint32(buf), 0, FILE_BUF_SIZE);
|
memset(PtrUInt(buf), 0, FILE_BUF_SIZE);
|
||||||
driver.storage.vfs.ReadFile(fHandle, 0, puint8(buf), FILE_BUF_SIZE - 1);
|
driver.storage.vfs.ReadFile(fHandle, 0, puint8(buf), FILE_BUF_SIZE - 1);
|
||||||
driver.storage.vfs.CloseFile(fHandle);
|
driver.storage.vfs.CloseFile(fHandle);
|
||||||
if state^.currentPath <> nil then kfree(void(state^.currentPath));
|
if state^.currentPath <> nil then kfree(void(state^.currentPath));
|
||||||
@@ -943,7 +928,7 @@ begin
|
|||||||
|
|
||||||
{ Allocate and zero-initialise state }
|
{ Allocate and zero-initialise state }
|
||||||
state := PNotepadState(kalloc(sizeof(TNotepadState)));
|
state := PNotepadState(kalloc(sizeof(TNotepadState)));
|
||||||
memset(uint32(state), 0, sizeof(TNotepadState));
|
memset(PtrUInt(state), 0, sizeof(TNotepadState));
|
||||||
state^.win_id := wid;
|
state^.win_id := wid;
|
||||||
state^.sel_anchor := -1;
|
state^.sel_anchor := -1;
|
||||||
addInstance(state);
|
addInstance(state);
|
||||||
|
|||||||
+30
-12
@@ -20,8 +20,8 @@ procedure init();
|
|||||||
implementation
|
implementation
|
||||||
|
|
||||||
uses
|
uses
|
||||||
arch.x86.bda, driver.net.types, driver.net.proto.icmp, driver.net.util, core.strings,
|
proc.types, driver.net.types, driver.net.proto.icmp, driver.net.util, core.strings,
|
||||||
proc.mgr, core.util, arch.x86.util, memory.heap;
|
proc.mgr, core.util, arch.platform.cpu, memory.heap;
|
||||||
|
|
||||||
const
|
const
|
||||||
PING_TIMEOUT_MS = 5000; { 5-second timeout per app.ping }
|
PING_TIMEOUT_MS = 5000; { 5-second timeout per app.ping }
|
||||||
@@ -31,22 +31,34 @@ type
|
|||||||
PPingState = ^TPingState;
|
PPingState = ^TPingState;
|
||||||
TPingState = record
|
TPingState = record
|
||||||
Result : TPingResult;
|
Result : TPingResult;
|
||||||
ReplyTimeMS : uint64;
|
ReplyTimeMS : uint32;
|
||||||
ErrorReason : TARPErrorCode;
|
ErrorReason : TARPErrorCode;
|
||||||
SendTime : uint64;
|
SendTime : uint32;
|
||||||
|
Address : puint8;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
procedure cleanup(handle: void);
|
||||||
|
var
|
||||||
|
st: PPingState;
|
||||||
|
begin
|
||||||
|
st := PPingState(handle);
|
||||||
|
if st = nil then exit;
|
||||||
|
driver.net.proto.icmp.cancelRequests(handle);
|
||||||
|
kfree(void(st^.Address));
|
||||||
|
kfree(handle);
|
||||||
|
end;
|
||||||
|
|
||||||
{ ---- ICMP callbacks (called from network recv context) ---- }
|
{ ---- ICMP callbacks (called from network recv context) ---- }
|
||||||
|
|
||||||
procedure on_reply(hdr : PICMPHeader; userData : void);
|
procedure on_reply(hdr : PICMPHeader; userData : void);
|
||||||
var
|
var
|
||||||
st : PPingState;
|
st : PPingState;
|
||||||
t2 : uint64;
|
t2 : uint32;
|
||||||
begin
|
begin
|
||||||
st := PPingState(userData);
|
st := PPingState(userData);
|
||||||
if st = nil then exit;
|
if st = nil then exit;
|
||||||
t2 := Counters.c64;
|
t2 := networkTicks;
|
||||||
st^.ReplyTimeMS := t2 - st^.SendTime;
|
st^.ReplyTimeMS := (uint64(uint32(t2 - st^.SendTime)) * 1000) div 1024;
|
||||||
st^.Result := prGotReply;
|
st^.Result := prGotReply;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@@ -87,24 +99,31 @@ begin
|
|||||||
|
|
||||||
{ Allocate per-invocation state so concurrent pings are safe }
|
{ Allocate per-invocation state so concurrent pings are safe }
|
||||||
st := PPingState(kalloc(sizeof(TPingState)));
|
st := PPingState(kalloc(sizeof(TPingState)));
|
||||||
|
if st = nil then begin
|
||||||
|
kfree(void(ip));
|
||||||
|
exit;
|
||||||
|
end;
|
||||||
|
st^.Address := ip;
|
||||||
|
proc.mgr.bindResource(proc.mgr.CurrentProcess, rkCustom, void(st), @cleanup);
|
||||||
timeoutTicks := (PING_TIMEOUT_MS * 1024) div 1000;
|
timeoutTicks := (PING_TIMEOUT_MS * 1024) div 1000;
|
||||||
|
|
||||||
for i := 0 to 9 do begin
|
for i := 0 to 9 do begin
|
||||||
{ Send ICMP echo request }
|
{ Send ICMP echo request }
|
||||||
st^.Result := prWaiting;
|
st^.Result := prWaiting;
|
||||||
st^.SendTime := Counters.c64;
|
st^.SendTime := networkTicks;
|
||||||
driver.net.proto.icmp.sendICMPRequest(ip, i, 128, @on_reply, @on_error, void(st));
|
driver.net.proto.icmp.sendICMPRequest(ip, i, 128, @on_reply, @on_error, void(st));
|
||||||
|
|
||||||
{ Spin-yield until callback fires or timeout }
|
{ Spin-yield until callback fires or timeout }
|
||||||
tStart := Counters.c32;
|
tStart := networkTicks;
|
||||||
while st^.Result = prWaiting do begin
|
while st^.Result = prWaiting do begin
|
||||||
proc.mgr.proc_yield;
|
proc.mgr.proc_yield;
|
||||||
tNow := Counters.c32;
|
tNow := networkTicks;
|
||||||
if tNow >= tStart then
|
if tNow >= tStart then
|
||||||
elapsed := tNow - tStart
|
elapsed := tNow - tStart
|
||||||
else
|
else
|
||||||
elapsed := ($FFFFFFFF - tStart) + tNow + 1;
|
elapsed := ($FFFFFFFF - tStart) + tNow + 1;
|
||||||
if elapsed >= timeoutTicks then begin
|
if elapsed >= timeoutTicks then begin
|
||||||
|
driver.net.proto.icmp.cancelRequests(void(st));
|
||||||
st^.Result := prGotError;
|
st^.Result := prGotError;
|
||||||
st^.ErrorReason := aecTimeout;
|
st^.ErrorReason := aecTimeout;
|
||||||
break;
|
break;
|
||||||
@@ -132,8 +151,7 @@ begin
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
{ Clean up }
|
{ Clean up }
|
||||||
kfree(void(st));
|
proc.mgr.unbindResource(proc.mgr.CurrentProcess, void(st));
|
||||||
kfree(void(ip));
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure init();
|
procedure init();
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ unit app.setres;
|
|||||||
interface
|
interface
|
||||||
|
|
||||||
uses
|
uses
|
||||||
io.stdio, driver.video.gpu, core.util, arch.x86.util, core.strings, debug.tracer, io.syslog;
|
io.stdio, driver.video.lvgl, driver.video.gpu, core.util, arch.platform.cpu, core.strings, debug.tracer, io.syslog;
|
||||||
|
|
||||||
procedure init();
|
procedure init();
|
||||||
|
|
||||||
@@ -25,6 +25,7 @@ var
|
|||||||
w, h : uint32;
|
w, h : uint32;
|
||||||
wStr, hStr : pchar;
|
wStr, hStr : pchar;
|
||||||
info : TGPUModeInfo;
|
info : TGPUModeInfo;
|
||||||
|
changed: boolean;
|
||||||
|
|
||||||
begin
|
begin
|
||||||
debug.tracer.push_trace('setres.run');
|
debug.tracer.push_trace('setres.run');
|
||||||
@@ -55,7 +56,10 @@ begin
|
|||||||
io.stdio.bufWriteStrLn(stdout_buf, 'x32...');
|
io.stdio.bufWriteStrLn(stdout_buf, 'x32...');
|
||||||
|
|
||||||
{ Step 1: Set display mode via GPU framework (tries BGA first, then VBE) }
|
{ Step 1: Set display mode via GPU framework (tries BGA first, then VBE) }
|
||||||
if not driver.video.gpu.setMode(w, h, 32, info) then begin
|
driver.video.lvgl.lvgl_lock;
|
||||||
|
changed := driver.video.gpu.setMode(w, h, 32, info);
|
||||||
|
driver.video.lvgl.lvgl_unlock;
|
||||||
|
if not changed then begin
|
||||||
io.stdio.bufWriteStrLn(stderr_buf, 'Error: Mode switch failed. Mode may not be supported.');
|
io.stdio.bufWriteStrLn(stderr_buf, 'Error: Mode switch failed. Mode may not be supported.');
|
||||||
debug.tracer.pop_trace;
|
debug.tracer.pop_trace;
|
||||||
exit;
|
exit;
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ unit app.uidebug;
|
|||||||
interface
|
interface
|
||||||
|
|
||||||
uses
|
uses
|
||||||
driver.video.lvgl, driver.video.windows, driver.hid.mouse, driver.video, arch.x86.multiboot, debug.tracer;
|
driver.video.lvgl, driver.video.windows, driver.hid.mouse, driver.video, boot.multiboot, debug.tracer;
|
||||||
|
|
||||||
{ Call once per frame from the main loop (before lvgl_handler). }
|
{ Call once per frame from the main loop (before lvgl_handler). }
|
||||||
procedure update;
|
procedure update;
|
||||||
|
|||||||
+55
-46
File diff suppressed because it is too large.
Load diff
@@ -36,6 +36,7 @@ var
|
|||||||
begin
|
begin
|
||||||
if heap = nil then exit;
|
if heap = nil then exit;
|
||||||
if heap^.Memory <> nil then begin
|
if heap^.Memory <> nil then begin
|
||||||
|
if heap^.PageCount <> 0 then
|
||||||
for i := 0 to heap^.PageCount - 1 do begin
|
for i := 0 to heap^.PageCount - 1 do begin
|
||||||
if heap^.Memory[i] <> nil then
|
if heap^.Memory[i] <> nil then
|
||||||
kfree(void(heap^.Memory[i]));
|
kfree(void(heap^.Memory[i]));
|
||||||
@@ -73,6 +74,7 @@ var
|
|||||||
begin
|
begin
|
||||||
if tables = nil then exit;
|
if tables = nil then exit;
|
||||||
if tables^.Tables <> nil then begin
|
if tables^.Tables <> nil then begin
|
||||||
|
if tables^.TableCount <> 0 then
|
||||||
for i := 0 to tables^.TableCount - 1 do begin
|
for i := 0 to tables^.TableCount - 1 do begin
|
||||||
if tables^.Tables[i].Elements <> nil then
|
if tables^.Tables[i].Elements <> nil then
|
||||||
kfree(void(tables^.Tables[i].Elements));
|
kfree(void(tables^.Tables[i].Elements));
|
||||||
@@ -90,6 +92,7 @@ var
|
|||||||
begin
|
begin
|
||||||
if ds = nil then exit;
|
if ds = nil then exit;
|
||||||
if ds^.Segments <> nil then begin
|
if ds^.Segments <> nil then begin
|
||||||
|
if ds^.SegmentCount <> 0 then
|
||||||
for i := 0 to ds^.SegmentCount - 1 do begin
|
for i := 0 to ds^.SegmentCount - 1 do begin
|
||||||
if ds^.Segments[i].Data <> nil then
|
if ds^.Segments[i].Data <> nil then
|
||||||
kfree(void(ds^.Segments[i].Data));
|
kfree(void(ds^.Segments[i].Data));
|
||||||
@@ -107,6 +110,7 @@ var
|
|||||||
begin
|
begin
|
||||||
if es = nil then exit;
|
if es = nil then exit;
|
||||||
if es^.Segments <> nil then begin
|
if es^.Segments <> nil then begin
|
||||||
|
if es^.SegmentCount <> 0 then
|
||||||
for i := 0 to es^.SegmentCount - 1 do begin
|
for i := 0 to es^.SegmentCount - 1 do begin
|
||||||
if es^.Segments[i].FuncIndices <> nil then
|
if es^.Segments[i].FuncIndices <> nil then
|
||||||
kfree(void(es^.Segments[i].FuncIndices));
|
kfree(void(es^.Segments[i].FuncIndices));
|
||||||
@@ -124,6 +128,7 @@ var
|
|||||||
begin
|
begin
|
||||||
if ts = nil then exit;
|
if ts = nil then exit;
|
||||||
if ts^.Types <> nil then begin
|
if ts^.Types <> nil then begin
|
||||||
|
if ts^.TypeCount <> 0 then
|
||||||
for i := 0 to ts^.TypeCount - 1 do begin
|
for i := 0 to ts^.TypeCount - 1 do begin
|
||||||
if ts^.Types[i].ParamTypes <> nil then
|
if ts^.Types[i].ParamTypes <> nil then
|
||||||
kfree(void(ts^.Types[i].ParamTypes));
|
kfree(void(ts^.Types[i].ParamTypes));
|
||||||
@@ -143,6 +148,7 @@ var
|
|||||||
begin
|
begin
|
||||||
if is_ = nil then exit;
|
if is_ = nil then exit;
|
||||||
if is_^.Entries <> nil then begin
|
if is_^.Entries <> nil then begin
|
||||||
|
if is_^.ImportCount <> 0 then
|
||||||
for i := 0 to is_^.ImportCount - 1 do begin
|
for i := 0 to is_^.ImportCount - 1 do begin
|
||||||
if is_^.Entries[i].ModuleName <> nil then
|
if is_^.Entries[i].ModuleName <> nil then
|
||||||
kfree(void(is_^.Entries[i].ModuleName));
|
kfree(void(is_^.Entries[i].ModuleName));
|
||||||
@@ -172,6 +178,7 @@ var
|
|||||||
begin
|
begin
|
||||||
if es = nil then exit;
|
if es = nil then exit;
|
||||||
if es^.Entries <> nil then begin
|
if es^.Entries <> nil then begin
|
||||||
|
if es^.ExportCount <> 0 then
|
||||||
for i := 0 to es^.ExportCount - 1 do begin
|
for i := 0 to es^.ExportCount - 1 do begin
|
||||||
if es^.Entries[i].Name <> nil then
|
if es^.Entries[i].Name <> nil then
|
||||||
kfree(void(es^.Entries[i].Name));
|
kfree(void(es^.Entries[i].Name));
|
||||||
@@ -189,6 +196,7 @@ var
|
|||||||
begin
|
begin
|
||||||
if cs = nil then exit;
|
if cs = nil then exit;
|
||||||
if cs^.Entries <> nil then begin
|
if cs^.Entries <> nil then begin
|
||||||
|
if cs^.CodeCount <> 0 then
|
||||||
for i := 0 to cs^.CodeCount - 1 do begin
|
for i := 0 to cs^.CodeCount - 1 do begin
|
||||||
if cs^.Entries[i].Code <> nil then
|
if cs^.Entries[i].Code <> nil then
|
||||||
kfree(void(cs^.Entries[i].Code));
|
kfree(void(cs^.Entries[i].Code));
|
||||||
|
|||||||
@@ -4,9 +4,7 @@
|
|||||||
Provides concrete WASI callback functions that route fd 0/1/2
|
Provides concrete WASI callback functions that route fd 0/1/2
|
||||||
to the owning Asuro process's StdIn/StdOut/StdErr buffers.
|
to the owning Asuro process's StdIn/StdOut/StdErr buffers.
|
||||||
|
|
||||||
An ActiveShim module-level variable is set before each tick batch
|
Hooks resolve the shim from the currently scheduled process.
|
||||||
and cleared after. Hooks only fire synchronously within wasm_tick
|
|
||||||
so this is safe under preemptive scheduling.
|
|
||||||
|
|
||||||
@author(Kieron Morris <kjm@kieronmorris.me>)
|
@author(Kieron Morris <kjm@kieronmorris.me>)
|
||||||
}
|
}
|
||||||
@@ -20,9 +18,7 @@ uses
|
|||||||
wasm.types.context,
|
wasm.types.context,
|
||||||
wasm.types.values;
|
wasm.types.values;
|
||||||
|
|
||||||
{ Set/clear the active shim — call before/after each tick batch }
|
|
||||||
procedure setActiveShim(shim : PProcessWASMShim);
|
|
||||||
procedure clearActiveShim;
|
|
||||||
|
|
||||||
{ WASI hook implementations — register via wasm_set_fd_write etc. }
|
{ WASI hook implementations — register via wasm_set_fd_write etc. }
|
||||||
function asuro_fd_write(fd : TWASMUInt32; buf : TWASMPUInt8; len : TWASMUInt32) : TWASMUInt32;
|
function asuro_fd_write(fd : TWASMUInt32; buf : TWASMPUInt8; len : TWASMUInt32) : TWASMUInt32;
|
||||||
@@ -46,19 +42,13 @@ implementation
|
|||||||
uses
|
uses
|
||||||
io.stdio, proc.types,
|
io.stdio, proc.types,
|
||||||
wasm.types.wasi, wasm.types.stack, wasm.types.heap,
|
wasm.types.wasi, wasm.types.stack, wasm.types.heap,
|
||||||
arch.x86.bda, core.rand, core.util, arch.x86.util;
|
proc.mgr, arch.platform.interrupts, arch.common.legacyirq, core.rand, core.util, arch.platform.cpu;
|
||||||
|
|
||||||
var
|
function ActiveShimPtr: PProcessWASMShim;
|
||||||
ActiveShimPtr : PProcessWASMShim;
|
|
||||||
|
|
||||||
procedure setActiveShim(shim : PProcessWASMShim);
|
|
||||||
begin
|
|
||||||
ActiveShimPtr := shim;
|
|
||||||
end;
|
|
||||||
|
|
||||||
procedure clearActiveShim;
|
|
||||||
begin
|
begin
|
||||||
ActiveShimPtr := nil;
|
ActiveShimPtr := nil;
|
||||||
|
if proc.mgr.CurrentProcess <> nil then
|
||||||
|
ActiveShimPtr := PProcessWASMShim(proc.mgr.CurrentProcess^.Local);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ ---- fd_write: fd 1 = stdout, fd 2 = stderr ---- }
|
{ ---- fd_write: fd 1 = stdout, fd 2 = stderr ---- }
|
||||||
@@ -81,7 +71,7 @@ begin
|
|||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
if outbuf = nil then exit;
|
if (outbuf = nil) or (len = 0) then exit;
|
||||||
|
|
||||||
{ Write byte-by-byte into the POutBuf }
|
{ Write byte-by-byte into the POutBuf }
|
||||||
for i := 0 to len - 1 do
|
for i := 0 to len - 1 do
|
||||||
@@ -111,7 +101,7 @@ begin
|
|||||||
avail := inbuf^.len;
|
avail := inbuf^.len;
|
||||||
if avail = 0 then exit;
|
if avail = 0 then exit;
|
||||||
if len < avail then copyLen := len else copyLen := avail;
|
if len < avail then copyLen := len else copyLen := avail;
|
||||||
memcpy(uint32(inbuf^.buf), uint32(buf), copyLen);
|
memcpy(PtrUInt(inbuf^.buf), PtrUInt(buf), copyLen);
|
||||||
asuro_fd_read := copyLen;
|
asuro_fd_read := copyLen;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@@ -126,13 +116,16 @@ begin
|
|||||||
ActiveShimPtr^.ProcessCtx^.ExitCode := code;
|
ActiveShimPtr^.ProcessCtx^.ExitCode := code;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ ---- clock_time_get: use BIOS tick counter ---- }
|
{ ---- Monotonic time from the platform timer ---- }
|
||||||
|
|
||||||
function asuro_clock_time_get(clock_id : TWASMUInt32; precision : TWASMUInt64;
|
function asuro_clock_time_get(clock_id : TWASMUInt32; precision : TWASMUInt64;
|
||||||
var time : TWASMUInt64) : TWASMUInt32;
|
var time : TWASMUInt64) : TWASMUInt32;
|
||||||
|
var
|
||||||
|
ticks: uint64;
|
||||||
begin
|
begin
|
||||||
{ Return time in nanoseconds based on BIOS 1024 Hz counter }
|
ticks := arch.platform.interrupts.timerTicks;
|
||||||
time := TWASMUInt64(arch.x86.bda.Counters.c64) * 976562;
|
time := (ticks div PIT_INPUT_HZ) * PIT_DIVISOR * 1000000000 +
|
||||||
|
((ticks mod PIT_INPUT_HZ) * PIT_DIVISOR * 1000000000) div PIT_INPUT_HZ;
|
||||||
asuro_clock_time_get := WASI_ESUCCESS;
|
asuro_clock_time_get := WASI_ESUCCESS;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@@ -141,7 +134,7 @@ end;
|
|||||||
function asuro_clock_res_get(clock_id : TWASMUInt32;
|
function asuro_clock_res_get(clock_id : TWASMUInt32;
|
||||||
var resolution : TWASMUInt64) : TWASMUInt32;
|
var resolution : TWASMUInt64) : TWASMUInt32;
|
||||||
begin
|
begin
|
||||||
resolution := 976562; { ~0.977ms in nanoseconds (1/1024 s) }
|
resolution := (uint64(PIT_DIVISOR) * 1000000000 + PIT_INPUT_HZ - 1) div PIT_INPUT_HZ;
|
||||||
asuro_clock_res_get := WASI_ESUCCESS;
|
asuro_clock_res_get := WASI_ESUCCESS;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
|||||||
Loaded 20 of 143 files, more files were not shown because too many files have changed in this diff.
Show more
Reference in new issue
Block a user