Implement built-in MEM command - #128
Conversation
|
👋 Jules, reporting for duty! I'm here to lend a hand with this pull request. When you start a review, I'll add a 👀 emoji to each comment to let you know I've read it. I'll focus on feedback directed at me and will do my best to stay out of conversations between you and other bots or reviewers to keep the noise down. I'll push a commit with your requested changes shortly after. Please note there might be a delay between these steps, but rest assured I'm on the job! For more direct control, you can switch me to Reactive Mode. When this mode is on, I will only act on comments where you specifically mention me with New to Jules? Learn more at jules.google/docs. For security, I will only act on instructions from the user who triggered this task. |
|
mem.c:439:14: warning: variable ‘xms_largest_free_kb’ set but not used [-Wunused-but-set-variable] |
|
You added empty commit, nice. |
|
Will do. I wonder if we can have unit tests somehow for our DOS based C code. |
|
For example by adding the "secret" |
|
Started as a PR against this PR, will have more of a look tomorrow. |
bf57f37 to
75ff233
Compare
|
rebase? |
|
This idiot Jules was reverting commits. |
5773e34 to
4239672
Compare
Report conventional, upper (UMB), reserved, extended (XMS) and expanded
(EMS) memory, the largest executable program size and the largest
available upper memory block, with /CLASSIFY, /FREE, /DEBUG, /PAGE and
/? switches. The report is laid out like the one real FreeDOS MEM
prints, and dosemu2's own test suite (test/func_comcom_internal.py)
compares the two tool's figures, so they follow MEM.EXE's conventions:
- memory is accounted for, and displayed, in KB. Each source is
converted to KB once, where it is read: INT 12h, XMS and INT
15h/E820h already report KB, EMS counts 16KB pages, and the MCB chain
is accumulated in paragraphs and converted at print time, rounding to
nearest. The largest blocks and the EMS totals also carry the byte
count MEM.EXE prints next to them;
- conventional memory ends at the 640K line, so its total is capped
there whatever INT 12h reports (dosemu2 with $_dosmem above 640
reports 736K), and an MCB crossing the line is split between the two
regions rather than charged whole to the one its first paragraph is
in: with UMBs linked, DOS merges the top of conventional memory with
the adjacent upper block into a single MCB;
- above it, the first megabyte is divided the way MEM.EXE divides it:
0xA000-0xDFFF is "Upper" and 0xE000-0xFFFF is "Reserved", both fixed
regions rather than sums of the blocks found in them, with free UMBs
counting towards upper memory wherever they sit;
- the largest free block is measured over runs of adjacent free blocks,
which DOS merges when it allocates - right after a program exits, the
memory it used is several adjacent free MCBs that have not been
merged yet, and reporting the largest of those understates what a
program can actually get by a wide margin.
Extended memory has no XMS call reporting the installed total, so it
comes from INT 15h/E820h, same as FreeDOS MEM: under dosemu2 the older
E801h/88h calls report a much smaller compatibility figure than the pool
that is actually configured. UMBs are linked for the scan through INT
21h/58h(03h) directly, so the allocation strategy is never touched. The
MCB walk stops if the chain fails to advance past 0xffff, rather than
wrapping into low memory and counting it twice.
MEM /CLASSIFY groups blocks by their owner. DOS 4+ records the owner's
name only in the MCB that holds the program itself, so the names are
collected up front and looked up by owner: naming each block on its own
listed one module twice, once as COMMAND and once as PSP-xxxx. The
placeholder blocks that keep the upper memory chain linked across the
video memory and the option ROMs ("SC", owned by the kernel) are holes
in the address space rather than memory, so they are listed but not
counted, and the memory below the first MCB is charged to SYSTEM, the
way MEM.EXE charges it.
/PAGE follows the cursor the way "dir /p" does instead of counting the
lines printed, since the report starts wherever the command line left
the cursor and long lines wrap. Built-in commands are handed only the
first argument, so "mem /d /p" would arrive as just "/d"; get_cmd_args()
exposes the full argument string for commands taking several switches.
tests/compare_mem.sh runs this MEM and the real FreeDOS MEM.EXE in one
dosemu2 session and compares them, as a stand-alone version of the
dosemu2 test. Both dosemu2 and FreeDOS come from the dosemu2 PPA: the
FreeDOS userspace, where MEM.EXE comes from, is installed by dosemu2's
own insfdusr into a private HOME under the cache dir, and
DOSEMU2_COMCOM_DIR points dosemu2 at the build under test.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Kg5AbDqjCHbxSZzSpV6aRA
4239672 to
4f749f1
Compare
|
Well, its new functionality, so it |
Implements a built-in MEM command similar to FreeDOS MEM in comcom64, placed in src/mem.c and src/mem.h. Updates build configurations (src/makefile.inc, djgpp/makefile) and registers 'mem' in command table in src/command.c.
PR created automatically by Jules for task 9759128799870124279 started by @stsp