Category : Files from Magazines
Archive   : VOL6N14.ZIP
Filename : PCMAP.ASM

 
Output of file : PCMAP.ASM contained in archive : VOL6N14.ZIP
;----------------------------------------------------------------------
; PCMAP - Search through memory and print out the program names (for
; DOS 3.x) and the number of bytes assigned to each in memory.
;----------------------------------------------------------------------
CSEG SEGMENT PARA PUBLIC 'CODE' ;Start CODE segment
ASSUME CS:CSEG,DS:CSEG,ES:CSEG,SS:CSEG ;Set by DOS Loader
ORG 100H ;COM file format

CR EQU 0DH ;Common equates
LF EQU 0AH
TAB EQU 09H

ENTPT: JMP PCMAP ;Jump over data

;======================================================================
COPYRIGHT DB "PCMAP 1.0 (c) 1987, Ziff-Davis Publishing Corp."
AUTHOR DB CR,LF,LF,'$',1AH,"Robert L. Hummel"

HEADING_MSG DB "Segment Paragraphs Program"
CR_LF_MSG DB CR,LF,'$'
COM_MSG DB "COMMAND.COM"
UNK_MSG DB "(Unknown)"
FREE_MSG DB "(Free)"
SPACE_MSG DB 7 DUP(' '),'$'
N_BLK DB 0 ;Count table entries
VER3 DB 0 ;=1 if Version 3.x

;======================================================================
PCMAP PROC NEAR

MOV DX,OFFSET COPYRIGHT
MOV AH,9 ;Display string
INT 21H ; Thru DOS

MOV AH,30H ;Check DOS version
INT 21H ; Thru DOS
CMP AL,3 ;If not 3.x
JB NOT_3 ; don't turn on flag
INC VER3 ; else, indicate
NOT_3:
;----------------------------------------------------------------------
; Find the first MCB by scanning through memory.
; On exit, ES points to the MCB.
; AX=Block Address, BX=ES, CX=Owner, DX=Top of memory.
;----------------------------------------------------------------------
XOR BX,BX ;Zero BX
SEARCH_MEM:
MOV ES,BX ;Point segment to 0
ASSUME ES:NOTHING ;Tell the assembler

CMP BYTE PTR ES:[0],'M' ;Is this a MCB?
JE CHECK_MCB ; might be
CRAWL:
INC BX ;Point to next segment
JMP SEARCH_MEM ; continue search
CHECK_MCB:
MOV AX,BX ;The MCB segment should
INC AX ; belong to the next segment
MOV CX,WORD PTR ES:[1] ;If owner of this block
CMP AX,CX ; is the same as the block
JNE CRAWL ; is first legitamate block
FOUND_FIRST:
MOV DX,WORD PTR DS:[2] ;Top of memory

;----------------------------------------------------------------------
; If the owner=0, then this block is unallocated (free).
; AX=Mem Address, BX=ES, CX=Owner, DX=Top of memory.
; Look up OWNER in table.
;----------------------------------------------------------------------
WORM_1:
CLD ;String moves forward
MOV DI,OFFSET TABLE ;Where to look

MOV CX,WORD PTR ES:[1] ;Get owner of this block
MOV AL,N_BLK ; number to look at
SEARCH_TABLE:
OR AL,AL ;If no entries are left
JZ CREATE_ENTRY ; create a new one
DEC AL ;Adjust valid entries

OR CX,CX ;If unallocated
JZ SKIP_ENTRY ; just skip to end

MOV SI,WORD PTR [DI] ;Get PID of owner
CMP CX,SI ;If owner matches
JE ADD_LEN ; add more length
SKIP_ENTRY:
ADD DI,17 ;Point to next entry
JMP SEARCH_TABLE

;----------------------------------------------------------------------
; Assume di points to 1st empty spot.
;----------------------------------------------------------------------
CREATE_ENTRY:
INC N_BLK ;Adding new entry
MOV AX,CX
OR CX,CX ;If block is free
JNZ NOT_FREE
MOV AX,BX ;Put mem address as owner
INC AX
NOT_FREE:
MOV WORD PTR [DI],AX ;Put owner in table
MOV WORD PTR [DI][2],0 ;Zero initial length
ADD_LEN:
MOV SI,WORD PTR ES:[3] ;Block Length

INC BX ;Use len to point bx...
MOV AX,BX ; (point AX to mem)
ADD BX,SI ;...to next MCB

ADD WORD PTR [DI][2],SI ;Increase para count

MOV SI,OFFSET FREE_MSG ;Memory is free
OR CX,CX ; if owner = 0
JNZ HAVE_OWNER
MOV CX,6 ;Length of string
JMP COPY_NAME ;Copy to TABLE
HAVE_OWNER:
;----------------------------------------------------------------------
; Is this block a primary (program) block?
;----------------------------------------------------------------------
CMP AX,CX ;Is mem = owner
JNE FIND_NEXT ;No

;----------------------------------------------------------------------
; This is a program block. Word at offset 2Ch into the block contains
; environment segment address. (offset from current ES by 1 paragraph)
;----------------------------------------------------------------------
MOV SI,WORD PTR ES:[2Ch+10h] ;Get env segment
CMP N_BLK,1 ;If not first block
JNE CHECK_ENV ; look for environment

MOV SI,OFFSET COM_MSG ;Put name in table
MOV CX,11 ;String length
COPY_NAME:
ADD DI,4 ;String destination
PUSH CS ;Point ES to
POP ES ; this segment
REP MOVSB ;Move the bytes
MOV AL,'$' ;DOS string terminator
STOSB ;Store it
PUSH CS ;Restore DS
POP DS
JMP SHORT FIND_NEXT

;----------------------------------------------------------------------
; Is the environment still allocated to the owner?
;----------------------------------------------------------------------
CHECK_ENV:
CMP VER3,0 ;If not 3.x
JE NO_ENV ; skip this section
DEC SI ;Point to env MCB
PUSH SI ;Put seg in DS

POP DS
CMP CX,WORD PTR DS:[1] ;Compare owners
JNZ NO_ENV ;Not our property

;----------------------------------------------------------------------
; Point DS:SI to the environment and scan for the double zero entry.
;----------------------------------------------------------------------
INC SI ;Point SI to environment
PUSH SI ; and put in DS
POP DS
XOR SI,SI ;DS:SI = ENV:0
INC SI
SCAN_ENV:
DEC SI ;Backup one byte
LODSW ;Look at word
OR AX,AX ;If not double 0 byte
JNZ SCAN_ENV ;Continue to look

;----------------------------------------------------------------------
; Find the end of the program pathname.
;----------------------------------------------------------------------
LODSW ;Skip a word (# strings)
MOV BP,SI ;Point to 1st char
DEC BP
SCAN_PATH:
LODSB ;Read char at SI
OR AL,AL ;If 0, end of string
JNZ SCAN_PATH ; else continue reading

;----------------------------------------------------------------------
; SI points past the terminating 0. Scan backwards for the \.
;----------------------------------------------------------------------
DEC SI ;Point SI to 0
MOV CX,SI ;Point CX past last char
SCAN_NAME:
DEC SI ;Point to char
CMP SI,BP ;Is it 1st char?
JE STRING_START
CMP BYTE PTR [SI],'\' ;It is backslash?
JNE SCAN_NAME ; no, continue
STRING_START:
INC SI ;Point to start of string
SUB CX,SI ;Length of string
JMP COPY_NAME ;Transfer
NO_ENV:
PUSH CS ;Restore DS
POP DS
MOV CX,9 ;Number of chars
MOV SI,OFFSET UNK_MSG ;Unknown
JMP COPY_NAME ;Transfer

;----------------------------------------------------------------------
; Point ES to next MCB and continue search. Stop at top of memory.
;----------------------------------------------------------------------
FIND_NEXT:
MOV ES,BX ;Set ES to next paragraph
CMP BX,DX ;At top of memory?
JE NO_MORE ; then done
JMP WORM_1 ;else continue
NO_MORE:
;----------------------------------------------------------------------
; Display the resulting table on the screen.
;----------------------------------------------------------------------
MOV DX,OFFSET HEADING_MSG ;Display the heading
MOV AH,9 ;Display string
INT 21H ; Thru DOS

MOV SI,OFFSET TABLE ;Table location
MOV CL,N_BLK ;Number of entries
XOR CH,CH ; as a word
PRINT_TABLE:
CALL PRINT_WORD ;Print owner
CALL PRINT_WORD ;and size

MOV DX,SI ;Name of owner
MOV AH,9 ;Display string
INT 21H ; Thru DOS
ADD SI,13 ;Point to next entry
MOV DX,OFFSET CR_LF_MSG ;Newline
MOV AH,9 ;Display string
INT 21H ; Thru DOS
LOOP PRINT_TABLE

MOV AH,4CH ;Terminate program
INT 21H ;Thru DOS

PCMAP ENDP

;======================================================================
PRINT_WORD PROC NEAR

LODSW ;Get owner
CALL HEX4 ;Write 4 digits
MOV DX,OFFSET SPACE_MSG ;space over
MOV AH,9 ;Display string
INT 21H ; Thru DOS
RET

PRINT_WORD ENDP

;======================================================================
; HEX4 - Write AX as 4 hex digits to console
; HEX2 - Write AL as 2 hex digits to console
;-----------------------------------------------------------------------------
HEX4 PROC NEAR

PUSH AX ;Save register
MOV AL,AH ;Show high digits first
CALL HEX2 ;Display AL
POP AX ;Restore low digits in AL

HEX2 PROC NEAR ;Display AL

PUSH AX ;Save register
PUSH CX ;Save CX during shift
MOV CL,4
SHR AL,CL ;Get high 4 bits
POP CX ;Restore CX

CALL H2C ;Display upper AL digit
POP AX ;Restore lower
AND AL,0FH ;Mask and display
H2C:
ADD AL,90H ;Convert AL to ASCII
DAA
ADC AL,40H
DAA

PUSH DX ;Save register during call
MOV DL,AL ;Character in DL
MOV AH,2 ;Display Output Fn
INT 21H ; Thru DOS
POP DX ;Restore register

RET

HEX2 ENDP
HEX4 ENDP

;======================================================================
; Format is TABLE DB 20 DUP (0,0, 0,0," ")
;----------------------------------------------------------------------
TABLE LABEL BYTE

;----------------------------------------------------------------------
CSEG ENDS
END ENTPT


  3 Responses to “Category : Files from Magazines
Archive   : VOL6N14.ZIP
Filename : PCMAP.ASM

  1. Very nice! Thank you for this wonderful archive. I wonder why I found it only now. Long live the BBS file archives!

  2. This is so awesome! 😀 I’d be cool if you could download an entire archive of this at once, though.

  3. But one thing that puzzles me is the “mtswslnkmcjklsdlsbdmMICROSOFT” string. There is an article about it here. It is definitely worth a read: http://www.os2museum.com/wp/mtswslnk/