diff --git a/build.bat b/build.bat index a03eb94..ca5e187 100644 --- a/build.bat +++ b/build.bat @@ -117,6 +117,13 @@ cd ..\kernel %MAKE% production if errorlevel 1 goto abort-cd +echo. +echo Process SETVER +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ +echo. +cd ..\setver +%MAKE% production +if errorlevel 1 goto abort-cd + cd .. set XERROR= diff --git a/clean.bat b/clean.bat index d755585..76a2bb1 100644 --- a/clean.bat +++ b/clean.bat @@ -27,6 +27,9 @@ cd ..\sys cd ..\kernel %MAKE% clean +cd ..\setver +%MAKE% clean + cd ..\hdr if exist *.bak del *.bak diff --git a/clobber.bat b/clobber.bat index 1d4b5c7..4c6d91d 100644 --- a/clobber.bat +++ b/clobber.bat @@ -27,6 +27,9 @@ cd ..\sys cd ..\kernel %MAKE% clobber +cd ..\setver +%MAKE% clobber + cd ..\hdr if exist *.bak del *.bak diff --git a/kernel/globals.h b/kernel/globals.h index 9c877cd..5bf5037 100644 --- a/kernel/globals.h +++ b/kernel/globals.h @@ -268,6 +268,8 @@ extern BYTE ASM ErrorMode, /* Critical error flag */ ASM CritErrClass, ASM VgaSet, ASM njoined; /* number of joined devices */ +extern VOID FAR * ASM setverPtr; /* Pointer to SETVER list */ + extern UWORD ASM Int21AX; extern COUNT ASM CritErrCode; extern BYTE FAR * ASM CritErrDev; diff --git a/kernel/kernel.asm b/kernel/kernel.asm index 2e287ca..b8b0047 100644 --- a/kernel/kernel.asm +++ b/kernel/kernel.asm @@ -407,7 +407,8 @@ _nul_dev: ; 0022 device chain root global _njoined _njoined db 0 ; 0034 number of joined devices dw 0 ; 0035 DOS 4 pointer to special names (always zero in DOS 5) -setverPtr dw 0,0 ; 0037 setver list + global _setverPtr +_setverPtr dw 0,0 ; 0037 setver list dw 0 ; 003B cs offset for fix a20 dw 0 ; 003D psp of last umb exec global _LoL_nbuffers diff --git a/kernel/task.c b/kernel/task.c index ad272c0..220cc0e 100644 --- a/kernel/task.c +++ b/kernel/task.c @@ -92,6 +92,44 @@ ULONG SftGetFsize(int sft_idx) return s->sft_size; } +STATIC WORD SetverCompareFilename(BYTE FAR *m1, BYTE FAR *m2, COUNT c) +{ + while (c--) + { + if (toupper(*m1) != toupper(*m2)) + { + return *m1 - *m2; + } + + m1 = m1 + 1; m2 = m2 + 1; + } + + return 0; +} + +STATIC UWORD SetverGetVersion(BYTE FAR *table, BYTE FAR *name) +{ + BYTE FAR *len; + COUNT nlen; + + if ((table != NULL) && (name != NULL)) + { + nlen = fstrlen(name); + + while (*(len = table) != 0) + { + if ((*len == nlen) && (SetverCompareFilename(name, table + 1, *len) == 0)) + { + return *((UWORD FAR *)(table + *len + 1)); + } + + table = table + *len + 3; + } + } + + return 0; +} + STATIC COUNT ChildEnv(exec_blk * exp, UWORD * pChildEnvSeg, char far * pathname) { BYTE FAR *pSrc; @@ -242,6 +280,7 @@ STATIC UWORD patchPSP(UWORD pspseg, UWORD envseg, exec_blk FAR * exb, mcb FAR *pspmcb; int i; BYTE FAR *np; + UWORD fakever; pspmcb = MK_FP(pspseg, 0); ++pspseg; @@ -287,6 +326,11 @@ set_name: if (i < 8) pspmcb->m_name[i] = '\0'; + if ((fakever = SetverGetVersion(setverPtr, np)) != 0) + { + psp->ps_retdosver = fakever; + } + /* return value: AX value to be passed based on FCB values */ return (get_cds1(psp->ps_fcb1.fcb_drive) ? 0 : 0xff) | (get_cds1(psp->ps_fcb2.fcb_drive) ? 0 : 0xff00); diff --git a/makefile b/makefile index 6b72daf..0f1aeb0 100644 --- a/makefile +++ b/makefile @@ -91,8 +91,8 @@ XUPX=upx --8086 --best XNASM=nasm ifeq ($(COMPILER),gcc) MAKE=make -MAKEADJUST=for i in utils lib drivers boot sys kernel; do sed 's@!include "\(.*\)"@include ../mkfiles/gcc.mak@' < $$i/makefile > $$i/GNUmakefile; done -MAKEREMOVE=for i in utils lib drivers boot sys kernel; do rm -f $$i/GNUmakefile; done +MAKEADJUST=for i in utils lib drivers boot sys kernel setver; do sed 's@!include "\(.*\)"@include ../mkfiles/gcc.mak@' < $$i/makefile > $$i/GNUmakefile; done +MAKEREMOVE=for i in utils lib drivers boot sys kernel setver; do rm -f $$i/GNUmakefile; done XLINK=ia16-elf-gcc else MAKE=wmake -ms -h @@ -115,6 +115,7 @@ all: cd boot && $(MAKE) production cd sys && $(MAKE) production cd kernel && $(MAKE) production + cd setver && $(MAKE) production $(MAKEREMOVE) clean: @@ -125,6 +126,7 @@ clean: cd boot && $(MAKE) clean cd sys && $(MAKE) clean cd kernel && $(MAKE) clean + cd setver && $(MAKE) clean $(MAKEREMOVE) clobber: @@ -135,4 +137,5 @@ clobber: cd boot && $(MAKE) clobber cd sys && $(MAKE) clobber cd kernel && $(MAKE) clobber + cd setver && $(MAKE) clobber $(MAKEREMOVE) diff --git a/setver/makefile b/setver/makefile new file mode 100644 index 0000000..6a2200b --- /dev/null +++ b/setver/makefile @@ -0,0 +1,17 @@ +# +# makefile for setver.sys +# + +!include "../mkfiles/generic.mak" + + +production: setver.sys + +setver.sys: setver.asm + $(NASM) -o ..$(DIRSEP)bin$(DIRSEP)setver.sys setver.asm + +clobber: clean + +clean: + -$(RM) *.obj *.map *.lst *.err + diff --git a/setver/setver.asm b/setver/setver.asm new file mode 100644 index 0000000..615bfde --- /dev/null +++ b/setver/setver.asm @@ -0,0 +1,81 @@ +; +; Initially written by Ricardo Hanke +; Released under the terms of the GNU General Public License. +; See the file 'COPYING' in the main directory for details. +; +; This driver loads the list of special programs into memory. +; + +section .text + + +COMMAND equ 2 +STATUS equ 3 +DRIVEREND equ 14 + +FAKETABLE equ 37h + + +header dw -1, -1 + dw 1000000000000000b + dw strategy + dw interrupt + db "SETVERXX" + + dw signature + +paramblock dd 0 + + +strategy: mov [cs:paramblock + 0], bx + mov [cs:paramblock + 2], es + retf + + +interrupt: push ax + push bx + push di + push es + pushf + + les di, [paramblock] + mov bl, [es:di + COMMAND] + cmp bl, 0 + jne error + + mov ax, table + add ax, [length] + + mov word [es:di + DRIVEREND + 0], ax + mov word [es:di + DRIVEREND + 2], cs + + mov ah, 52h + int 21h + + mov word [es:bx + FAKETABLE + 0], table + mov word [es:bx + FAKETABLE + 2], cs + + xor ax, ax + jmp exit + +error: mov ax, 8003h + +exit: or ax, 0100h + mov [es:di + STATUS], ax + + popf + pop es + pop di + pop bx + pop ax + + retf + + +signature db 'SDIR' +length dw 1 + +table ;db 11, "SHOWVER.EXE", 5, 00 + ;db 12, "BUGGYPRG.EXE", 3, 31 + + db 0