NASM - The Netwide Assembler

NASM Forum => Programming with NASM => Topic started by: whakamaru on March 19, 2014, 12:47:39 AM

Title: I don't know how to display the answer!
Post by: whakamaru on March 19, 2014, 12:47:39 AM
I can write asm. I solved ProjectEuler #303 using 16-bit and MS-debug. Now, I have worked out the logic to solve #401 but that needs 64 bit.  I have the answer in RAX
How do I display that in decimal please.  At C: prompt? or in a windows window?
Title: Re: I don't know how to display the answer!
Post by: Frank Kotler on March 19, 2014, 01:13:58 AM
Same as you'd do it with a smaller register - divide repeatedly by ten - I suppose. Do you know how to do that? "div" is a horribly slow instruction. There are faster ways to do it, but harder to understand (I stick with "div" myself, but gotta tackle the faster ways eventually...). There's also "just call printf". What are you looking for help with, and how far can you get with it?

Best,
Frank

Title: Re: I don't know how to display the answer!
Post by: whakamaru on March 19, 2014, 08:36:16 PM
In 16-bit I go...
mov bx,10
xor cx,cx
T1: xor dx,dx
div bx
push dx
inc cx
or ax,ax
jnz T1
T2: pop ax
add al,48
mov ah,e(h)
int 10(h)
loop T2
but... do the ROM interrupts work in 64-bit system?  My attempts don't go anywhere.  "printf"? I don't know what that does. Of course it is mentioned in the nasmdoc.txt, but not explained. 
I would love to know your "better than div" procedure?  thanks.
Title: Re: I don't know how to display the answer!
Post by: Rob Neff on March 19, 2014, 08:46:29 PM
but... do the ROM interrupts work in 64-bit system?

Nope, not at all in userland programs.  It wouldn't be a very Protected-Mode Operating System if it allowed you to do this.
You may try accomplishing something like that in a virtual machine environment using something like DOSBox.  I don't use that so I'm not of much further help.

Title: Re: I don't know how to display the answer!
Post by: Frank Kotler on March 19, 2014, 11:42:54 PM
Well, BIOS interrupts are 16-bit, so would work in DOS, DosBox, or "my own OS" (until you switch to pmode). For a "real OS" (protected from US!), we need to talk to the OS - WriteFile or WriteConsole (heck, MessageBoxA would do it) for Windows. I use sys_write in Linux (should work for OSX too). I get the impression you're using Windows... which I know less about...

In the method you show, we push the remainders on the stack and pop 'em off to get 'em in the "right order", since they appear rightmost first and we print leftmost first. Instead, we could put 'em in a buffer, starting at the "top" or right end of the buffer and work back to the "beginning". We may want to start with a zero (the number 0, not the character '0') to make a zero-terminated string. When we run out of digits (quotient is zero) we probably aren't at the "beginning" of the buffer. We could save this position as the "start print"
 position, or we could space-pad to the beginning of the buffer (right-justified numbers look better if we're printing a column of numbers). Once we've got 'em in a buffer, it's pretty much "hello world".

To eliminate the slow "div"... Hmmm... I think "Brethren" has got an example in the "example code" section here. I'll look for that. "Terje's method"  (Terje Mathisen) may be better - the AMD optimization manual has that (don't credit him - maybe they developed it independently) and I think Agner Fog's work uses it. I'm gonna have to "get back to you" on that... Remind me if I don't...

Later,
Frank

Title: Re: I don't know how to display the answer!
Post by: whakamaru on March 26, 2014, 10:01:01 PM
I tried printf. NASM produced the .OBJ, but GOLINK said.... "printf not defined".  So, what now?
I also tried "WriteFile" as described in one of the examples.  NASM didn't like that at all, every ARG produced a "instruction expected" error
Many years ago, I knew that QBASIC sent its output directly to a screen buffer in memory.  That might work now?  Alas, I don't remember the way to do it, and didn't keep the programs I wrote that used the method.
Title: Re: I don't know how to display the answer!
Post by: Rob Neff on March 26, 2014, 11:32:19 PM
I tried printf. NASM produced the .OBJ, but GOLINK said.... "printf not defined".  So, what now?

That's a linker error.  You need to specify the libraries containing the functions you use.
Title: Re: I don't know how to display the answer!
Post by: Frank Kotler on March 29, 2014, 05:33:50 AM
The "direct to screen memory" method no longer works. In a multi-user multi-tasking OS, you wouldn't want to do it even if you could - it might not be "your turn" - might not "have the focus". Unfortunately...

I don't know much about Windows, but they spell it "_main", "_printf", etc. If you've got source without the underscores, adding "--prefix _" to Nasm's command line will add an underscore to anything declared "extern" or "global". I think the true name of "WriteFile" is "_WriteFile@20". That may not be correct for 64-bit code. You may need to show us exactly what you tried - the command line to GOLINK, in particular. As Rob indicates, that's critical.

I haven't done anything with the "better than div" method, but I haven't forgotten you. Like the careless butcher, I've gotten a little behind in my work. :)

Best,
Frank

Title: Re: I don't know how to display the answer!
Post by: encryptor256 on March 29, 2014, 01:37:08 PM
The "direct to screen memory" method

This might help or not, something similar.
It is available on windows via WinAPI, GUI applications,
function named: CreateDIBSection ( MSDN: CreateDIBSection (http://msdn.microsoft.com/en-us/library/windows/desktop/dd183494%28v=vs.85%29.aspx) ),
it gives a pointer to image raw data and can be used in conjunction with WinAPI drawing functions.

Title: Re: I don't know how to display the answer!
Post by: Frank Kotler on March 29, 2014, 02:52:51 PM
That would probably be fantastic, but I think what we need is "hello world" and work up to it. Whakamaru has a "number to ascii" routine that would probably work if the registers had an "r" in front of them - except for the BIOS interrupt. I think he's probably better off to put the characters in a buffer and print 'em all at once, rather than one at a time, but either would do...

It occurs to me that errors on "ARG" suggest a missing include file, no?

Best,
Frank