Hi,
Here is a small program that I coded to execute another program.
http://rapidshare.com/files/2394260/EXEC.rar
The fact is that,It doesn't work properly.
I don't know where in the code is wrong and that's why I need your help.
In fact,my aim is to learn how to code a small program which supports Overlays.
So, as the first step I should learn the way we execute other programs.
Pleasle help me in this case.
Regards,
Zest.
TITLE A PROGRAM TO EXECUTE ANOTHER ONE
PAGE 62,133
stseg SEGMENT STACK
BYTE 64 DUP (?)
stseg ENDS
dtseg SEGMENT PUBLIC 'DATA'
PathName BYTE "C:\v.exe",0
ParamBlock WORD 0
DWORD CmdLine
DWORD Dummy,Dummy
CmdLine BYTE 4,'v.exe',0dh
Dummy BYTE 20 DUP (?)
dtseg ENDS
cdseg SEGMENT PUBLIC 'CODE'
main PROC FAR
ASSUME cs:cdseg,ds:dtseg,ss:stseg,es:dtseg
mov ax,SEG dtseg
mov ds,ax
mov es,ax
mov ah,4Bh
mov al,0
mov dx,SEG PathName
mov ds,dx
lea dx,PathName
mov bx,SEG ParamBlock
mov es,bx
lea bx,ParamBlock
int 21h
;Wait for keypress
xor ah,ah
int 16h
mov ah,4ch
int 21h
main ENDP
cdseg ENDS
PUBLIC main
END main
One of the first things to do in a DOS EXE is to adjust your memory, since DOS usually allocates all available memory to the EXE.
When debugging execute.exe, DOS returns with error 8 (no memory) when it tries to EXEC v.exe.
If I have a problem like this I try to fix it in tiny steps.
I would make a tiny program to enable another tiny program, like printing a single letter or pixel.
...then spend the next 3 days trying to figure out wtf is going on. :bg
Quote from: eek on November 08, 2006, 12:58:49 PM
If I have a problem like this I try to fix it in tiny steps.
I would make a tiny program to enable another tiny program, like printing a single letter or pixel.
...then spend the next 3 days trying to figure out wtf is going on. :bg
Your best friend (really) is DEBUG.EXE and the commands T and P :bg
Quote from: sinsi on November 08, 2006, 07:38:01 AM
One of the first things to do in a DOS EXE is to adjust your memory, since DOS usually allocates all available memory to the EXE.
When debugging execute.exe, DOS returns with error 8 (no memory) when it tries to EXEC v.exe.
Thanks for the reply.
But could you please let me know the way I can allocate memory for my propgram?
Please explain the process.
Best Regards,
Zest.
> But could you please let me know the way I can allocate memory for my propgram?
as stated by sinsi, you have to free some DOS memory used by your program *before* you call int 21h, ah=4Bh. This is usually done by calling int 21h, ah=4Ah and register BX set to the amount of paragraphs your program needs to run.
How to calculate this amount?
ES:0000 is the start of the memory block you are using, and SS:SP points to the end of it.
Now you have to calculate the difference and transform it to paragraphs. I guess you can do this task on your own :).
Quote from: japheth on November 09, 2006, 11:18:00 AM
ES:0000 is the start of the memory block you are using, and SS:SP points to the end of it.
By the looks of the segment layout, the last segment is actually cdseg not the stack. I would either make stseg the last segment, or
use .model and .dosseg - this way you can use .startup and .exit which will make it a lot easier. Also, 64 bytes is a little small for a stack, even
in DOS - I usually use a 4k stack, since things like XMS require at least 1k of your stack for their use.
Hi,
Thanks for your hints and explanations.
According to what you friends said I did the following.
Let me know if I still have mistakes in this program.
1- I changed the stak segment to this shape.
.DOSSEG
stseg SEGMENT PARA STACK
BYTE 4096 DUP (?)
stseg ENDS
2-The I Computed the size of running program by following istructions.
mov bx,es ;Copy the first address memory into bx
mov ax,ss
add ax,sp ;Computing the size of this running program in paragraphs
sub ax,bx
xor cx,cx
mov cx,16
cwd
div cx
mov bx,ax ;Release unused memory
mov ah,4Ah
int 21h
In fact,"Int 21h with option 4Ah" asks me to direct Es into SEGMENT ADDRESS OF BLOCK.
I don't know this address and thus ignored it.
Let me know where it should point to.
Another question is that why we should use "Int 21h with option 4Ah" ?
I noticed that you want to resize the alocated memory and this action causes the memory to be deallocated and deallocation means having free memory.
The querstion is that why you don't use "int 21h with option 49h" which is specially designed to free up allocated memory.
Is there any way to use this interrupt?
3-This last question is about .DOSSEG Directive.
Here is what I found on NEt about this directive.
Quote.DOSSEG/DOSSEG
Orders the segments according to the DOS segment convention: CODE first, then segments not in DGROUP, and then segments in DGROUP. The segments in DGROUP follow this order:
1.Segments not in BSS or STACK
2.BSS segments
3.STACK segments
So it simply put the stack segment the last segment of your program.
But what I don't know is BSS segments.
What are BSS segments?
Could you please shed some light?
Thanks in advance.
Best Regards,
Zest.
Hi,
the code to calc the size of running program has a bug:
1.
mov bx,es
mov ax,ss
;; add ax,sp ;<- this cannot be added yet
sub ax,bx
mov cx,sp ;convert SP to paragraph "units"
shr cx,4
inc cx
add ax,cx ;<- and then add here
; xor cx,cx ;these 4 lines are not needed
; mov cx,16 ;since ax already contains paragraphs
; cwd
; div cx
> In fact,"Int 21h with option 4Ah" asks me to direct Es into SEGMENT ADDRESS OF BLOCK.
> I don't know this address and thus ignored it.
ES happens to contain that address already. So it is ok to ignore it in this case.
> Is there any way to use this interrupt?
No, int 21h, ah=4Ah must be used, since your program resides in one large memory block whose size has to be reduced, but the block itself cannot be freed.
Hi,
Thanks for your help.
But I have some questions regarding your algo.
First, you didn't use DIV instruction.
Why did you use SHR instruction?
Does it make any difference?
Second,you just calculated the Paragraph size for the stack,so what about the difference we have between "ss - es = " ?
I mean by subtracting ss from es you will have a number which is the difference between two different segments.
What about this number?
Shouldn't we divide it by 16 to get how many paragraph units are between them?
Third,why did you add one to the result?
I mean what's the role of INCREMENT instruction in your algo?
Maybe,this is because SHR rounds down the result and you increment one to it, to round up the result,like what division instruction do.
I really don't know the fact and I just guess, which might cause you laugh.
:red
Thanks in advance.
Best Regards,
Zest.
Hi,
> First, you didn't use DIV instruction.
> Why did you use SHR instruction?
> Does it make any difference?
Yes, it is 0,2 ns faster. For an assembly coder, every nanosecond counts.
> Shouldn't we divide it by 16 to get how many paragraph units are between them?
no, since the segment registers already contain paragraph-related addresses.
> Maybe,this is because SHR rounds down the result
Yes. However, this might waste 16 bytes precious DOS memory if the lower 4 bits were already zero. If the launched program needs these 16 bytes desperately, you will have to adjust the algorithm.
Regards
Japheth
Hi,
Thanks for clarifying the obscure cases.
I still have a few minor questions.
1-I understood the fact about segment registers.
I think this is because we declared them in the program this type:
stseg SEGMENT STACK
BYTE 64 DUP (?)
stseg ENDS
In this case the default type is PARA .
But what if they are declared this type:
stseg SEGMENT PAGE STACK
BYTE 64 DUP (?)
stseg ENDS
Shall I write an algo to change the PAGE to byte and then Byte to Paragraph?
2-I think that here, we are calculating logical memory addresses.
Am I right?
Does calculating physical memory addresses make difference in our results?
By saying "calculating physical memory addresses " ,I mean shifting segment addresses 4 bits left and then adding them to instruction counter of that segment.
Here it's SP.
I just want to know if by doing so we will get any better or more precise result in performance.
Thanks.
Best Regards,
Zest.
As far as alignment goes (PARA/PAGE) this decides where the segment starts -
PARA will start on a 16-byte boundary
PAGE will start on a 256-byte boundary
so the assembler will insert nulls in the preceding segment to align the segment. In theory, you could waste 255 bytes by using PARA e.g.
dtseg SEGMENT
var1 BYTE 1
dtseg ENDS
stseg SEGMENT PAGE
BYTE 64 dup (?)
stseg ENDS
say dtseg is at address 1000:0000 then stseg will be at 1010:0000 (which is also 1000:0100, just to confuse us all) because the assembler
pads dtseg with 255 bytes of crap to make it to the next page (100h bytes, 10h paragraphs). I reckon stick to the default PARA in 16-bit DOS.
With physical/logical addressing, 16-bit real mode uses segmented addressing (segment:offset) to get a 20-bit physical address -
ssss ;eg F123
oooo ;eg 01A9
ppppp ;eg F13D9
and just to finish on a confusing note, a 20-bit address can be one of 4096 segment:offset addresses...
Hi,
Thanks for explanation.
Ok.
Now I need more help.
I want to make the situation more complicated.
If you look at the first post in this topic,you'll see that I put zero in AL to load and execute the second program.
In fact,in thsi part:
mov ah,4Bh
mov al,0
mov dx,SEG PathName
mov ds,dx
lea dx,PathName
mov bx,SEG ParamBlock
mov es,bx
lea bx,ParamBlock
int 21h
Now,I want to put one in Al and just load the second program.
Then I want to change one byte of the second program.(For example the string which is used in V.EXE to show DOS version) And at last I want to run the second program while it's changed already by the First program.
So what should I do after loading the second program by putting 1 in AL.
How can I access to the elements of the second program.
For example data segment and code segment.
Also let me know how to run the second program after changing some of its parts.
Please explain it well or just show me a snippet of code.
So I can understand this concept in coding.
Thanks in advance.
Best Regards,
Zest.
Hi,
Is there any problems or ambiguous parts in my previous post?
Please let me know if your need more explanation of what I want to do.
Also please let me know how you make OVR files.
As far as I know OVR files are used as overlay files.
Thanks in advance.
Best Regards,
Zest.
Quote
Format of EXEC parameter block for AL=00h,01h,04h:
Offset Size Description (Table 01590)
00h WORD segment of environment to copy for child process (copy caller's
environment if 0000h)
02h DWORD pointer to command tail to be copied into child's PSP
06h DWORD pointer to first FCB to be copied into child's PSP
0Ah DWORD pointer to second FCB to be copied into child's PSP
0Eh DWORD (AL=01h) will hold subprogram's initial SS:SP on return
12h DWORD (AL=01h) will hold entry point (CS:IP) on return
Look at offset 12h, this gives you the entry for the other program.
As far as changing bytes in the program, if you know the code of it then the CS:IP will give
you an idea of addresses - if you don't then you shouldn't be hacking it in the first place.
Hi,
Thanks sinsi for your help.
I fixed this part as follows:
ParamBlock LABEL WORD
WORD 0
DWORD CmdLine
DWORD DfltFCB,DfltFCB
LoadSSSP DWORD ?
LoadCSIP DWORD ?
Then I used this code to change and then enter to the second program:
mov bx,SEG ParamBlock ;Loading the Child Process
mov es,bx
mov bx,ParamBlock
lds dx,PgmName
mov al,01h
mov ah,4bh
int 21h
mov es,WORD PTR cs:[LoadCSIP] ;Trying to change the twentieth Byte in
mov si,20h ;the second program
mov BYTE PTR es:[si],'$'
mov ss,WORD PTR cs:[LoadSSSP] ;Trying to go to the second program and
mov sp,WORD PTR cs:[LoadSSSP]+2 ;executing it
jmp DWORD PTR cs:[LoadCSIP]
mov ah,4ch
int 21h
Unfortunately,It doesn't work.
I have some questions to be able to understand the concept.
When the second program is loaded,where is it located?
Is it right after the stack segment of the first program?
If it's so,I should be able to search in the memory for the bytes I want.
But I need an algo to search in memory.
ss of the parent program is the last segment wihch I should use and add sp to it to get the last address in the memory.
After this address normally the first segment of the child program should be loaded.
How can I code an algo to search in this area?
Also what is the last address in the memory?
I mean how far shall I do search in memory to find the desired bytes.
Is there any way to use SCASB instruction to find the place in memory?
In fact,let me know what should be put in ES:DI and AL and CX to be able to use SCAS instruction.
As for being legal or not,I just want to change my previous program which shows DOS Version.
Here is the program and it's souurce code that I want to change.
http://rapidshare.com/files/3490689/Load.rar
I want to change this part in this program:
mov dl,'.'
mov ah, 02h
int 21h
to
mov dl,'*'
mov ah, 02h
int 21h
So I should find the first part in RAM and then try to replace it with the second part.
The problem is coding this algo.
I hope you can help.
Thanks in advance.
Regards,
Zest.
The (LoadCSIP DWORD) is actually stored as (WORD offset,segment) and points to the start: label, so you would
have to calculate the difference between start: and the byte to change.
QuoteAs for being legal or not,I just want to change my previous program which shows DOS Version
Much easier to change source code...
This seems to be a bit dodgy, so I suggest you read the rules of the forum. I see the other forum locked your topic - don't be suprised
if this one is too.
Zest,
So you are going to the trouble of coding a program, to change just one byte, in your own application, when you have the source code for the application, and even if you didn't there would be much easier methods. What are you really trying to do?
Hi,
Thanks.
So to avoid being banned,I change the focus of this topic to using Overlays.
I mean this fuction which is the last one I want to learn.
Using interrupt 21h function al=3h and ah=4Bh
I know that I should use this ParamBlock
ParamBlock LABEL WORD
StartSeg WORD ?
RelocFactor WORD 0
But what should be put in the first member of this block?
I mean this: StartSeg WORD ?
Also in previous programs we used an address and the second program name to point to the second program which is used for loading.
For example:
PathName BYTE 'C:\v.exe',0
And it's used in this part of the program:
mov ah,4Bh
mov al,3
mov dx,SEG PathName
mov ds,dx
lea dx,PathName
mov bx,SEG ParamBlock
mov es,bx
lea bx,ParamBlock
int 21h
Now I want to know this time,what this element should point to.
I also have seen some files with this extension.
*.OVR
These files are seemingly ,Overlay files.
Could you please let me know how it is possible to compile and make such files?
Do you use any special option with Assembler or Linker to compile such files?
By the way,you didn't talk about the algo which its aim is to search in memory.
Is it possible to write such an algo?
I hope coding such an algo is not illegal.
Thanks in advance.
Best Regards,
Zest.
Quote from: MichaelW on November 16, 2006, 07:27:50 AM
Zest,
So you are going to the trouble of coding a program, to change just one byte, in your own application, when you have the source code for the application, and even if you didn't there would be much easier methods. What are you really trying to do?
Hi,
The answer is that I want to learn this function of interrupt 21h.
That's why I coded a small program of mine,to be able to learn the behaviour of this undocumented fuction.
What I mostly Like to learn is everything which deals with Computer Memory and its strcuture.
These topics are not popular and that's why most of programers don't know anything about them.
Some also know but don't care to share.
Some are also wicked ones.
By wicked I mean a great programmer in Leggal coding forums like this and simultaneously a great cracker in illegal forums like that.
So when I try to ask about something which is used mostly by wicked ones,the arguments will arise.
I can understand that,but what I can't understand is that why I should for learning a legal function
which is a part of pure programming provided by MICROSOFT go to illegal forums and ask for help.
:(
Still,I beleive that there,at illegal forums,wicked ones are silent.
The help there, will come from a great programmer who is not evil at heart.
A person who beleives in faithfulness,honesty and truthfulness of human beings.
That's the bitterness of the truth.
Best Regards,
Zest.
> I also have seen some files with this extension.
> *.OVR
> These files are seemingly ,Overlay files.
> Could you please let me know how it is possible to compile and make such files?
> Do you use any special option with Assembler or Linker to compile such files?
> By the way,you didn't talk about the algo which its aim is to search in memory.
> Is it possible to write such an algo?
Your questions suggest that you know almost nothing about DOS programming. Your "project" is too ambitious
for your skills. Thus all you can do is request others to feed you with information, which is not the purpose of this forum. No!
Quote from: japheth on November 16, 2006, 10:56:03 AM
> I also have seen some files with this extension.
> *.OVR
> These files are seemingly ,Overlay files.
> Could you please let me know how it is possible to compile and make such files?
> Do you use any special option with Assembler or Linker to compile such files?
> By the way,you didn't talk about the algo which its aim is to search in memory.
> Is it possible to write such an algo?
Your questions suggest that you know almost nothing about DOS programming. Your "project" is too ambitious
for your skills. Thus all you can do is request others to feed you with information, which is not the purpose of this forum. No!
Hi japheth,
Everybody has an opinion which is honorable and I respect yours.
Maybe,my project which is just learning is ambitious for my skills and I don't know anything about programming.
So,I need help to overcome this problem.
If the perpose of this board is not to teach and solve others problems,there is still no complaining.
In some previous posts I mentioned that if there were sorce codes for what I asked please let me know.
Source codes are mostly from the programs which were written by some coders that they made these codes public or they are from Books.
If you still don't know any public source code which can help me ,just introduce a book which can cover the topics I need to know and I have to know.
I promise to buy that book and read it from cover to cover and don't ask anything here.
By reading this book and learning it,rarely can be a man who can express that I don't know anything about programing.
However,not knowing about a case is not a big problem,but not asking is.
The sin is, knowing about not knowing of a case.
So I asked for informaton, to get and then by this information remedy the problem of not knowing or maybe the sin.
In conclusion, I still ask for introducing a book in which the topics I asked and I want to know and I have to know is covered.
Regards,
Zest.
Download and debug my programm.
I launch command.com.
http://www.masm32.com/board/index.php?topic=5032.0
Quote from: Rockphorr on November 16, 2006, 05:39:41 PM
Download and debug my programm.
I launch command.com.
http://www.masm32.com/board/index.php?topic=5032.0
Thank you so much Rockphorr.
:U
I'll study your code.
Regards,
Zest.
Zest,
Function 4B01h, Load Program, was originally undocumented, but Microsoft had officially documented it by 1991 (MS-DOS 5.0). The use of the function was covered in detail in Chapter 7 of the first edition of UNDOCUMENTED DOS: A Programmer's Guide to Reserved MS-DOS Functions and Data Structures by Andrew Schulman, Raymond J. Michels, Jim Kyle, Tim Paterson, David Maxey, and Ralf Brown, Addison-Wesley, 1990, ISBN 0-201-57064-5. Chapter 7, titled The MS-DOS Debugger Interface, was written by Tim Paterson, who developed the 16-bit x86 OS that eventually became MS-DOS Version 1.0. IIRC that chapter was missing in the second edition, and both editions are out of print.
Calling the function is straight forward, but passing control to the loaded program, and then back to the calling program when the loaded program terminates, is somewhat difficult. Before you pass control to the loaded program, you must set the segment registers and stack pointer as Function 4B00h would. When control returns to the calling program, you must set the segment registers (other than CS) and stack pointer to values that are correct for the calling program, in the state it was in when it performed the call. This is much easier to do if both of the programs are COM files and the calling program has nothing essential on the stack (so you can just leave SP as is). Some other important details are:
The function sets the current PSP to that of the loaded program, so between the function call and the point at which control is passed to the loaded program the calling program cannot do I/O through DOS. Or at least not without first making the current PSP that of the calling program, but the loaded program's PSP (segment address) must be preserved, because it will be needed to set DS and ES, and it must be the current PSP when control is passed to the loaded program. When control returns to the calling program, the current PSP is that of the calling program.
Control can be passed to the loaded program by doing a far call to the far address that the function places in the ldCSIP member of the LOAD structure (these are the documented Microsoft names for the LoadCSIP and ParamBlock in your code).
Hi MichaelW,
Thanks for your explanation and attention.
Unfortunately my last hope which was buying the books is dead.
:(
The book which I could study and see its source codes is out of print and I just can hear in here and there that the only good book for my purposes in learning and programming is out of print.
Someone esle mentioned that what I need is a book about system programming in assembly.
Then he introduced this book which is out of print indeed. :(
QuoteAssembly Language Master Class (Wrox Press Master Class) (Paperback)
by Igor Chebotko, Peter Kalatchin, Yuri Kiselev, Efim Podvoisky, Kiril Malakhov, Yuri Petrenko, Mike Schmit, Sergei Shkredov, Gennady Soudlenkov, Daniel Wronski
(7 customer reviews)
* Paperback: 1024 pages
* Publisher: Apress; Bk&Disk edition (October 1994)
* Language: English
* ISBN: 1874416346
Do you know anything about this book?
Is it what I should look for?
I wish I could even buy the ebook of these ones.
The wonder is,while the publication doesn't publish the books and there is no money engaged in this case,why these books shouldn't be public and available for everyone who really needs them.
Anyway,it seems that I should follow my work with trial and error to get to the reasult which I become satisfy with.
Thanks anyway,
Best Regards,
Zest.