NASM - The Netwide Assembler
NASM Forum => Programming with NASM => Topic started by: XxWh1t3gh0stxX on November 28, 2012, 04:07:34 AM
-
I am trying to read from a file and display the ascii symbols, but when I read in values I either only get the actual text and not ascii symbols.
; Compiling this code for 32-bit use:
; nasm -f elf file.asm
;
;
;~.~. Definitions for readability: ~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
%define SYS_EXIT 1
%define SYS_READ 3
%define SYS_WRITE 4
%define STDIN 0
%define STDOUT 1
%define STDERR 2
;~.~. Initialized data: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
SECTION .data
Title: db 'title.txt', 0 ; Everything from title.txt
Board: db 'cBoard.txt', 0 ; Board
OpenFile: db 'r', 0 ; Opens an existing text file for reading
;~. Uninitialized data: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
SECTION .bss
TLENGTH EQU 72
tLENGTH resb TLENGTH
;~.~. Program code: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
SECTION .text
; Place all your extern declarations in this area.
extern fopen
extern fclose
extern fgets
extern printf
global main ; specify starting with main
main:
nop
xor ebx, ebx
mov ebx, Title
call DisplayTitle
xor ebx, ebx
mov ebx, Board
call DisplayBoard
jmp home
;~.~. Subroutines: ~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
; Place all your subroutine code in this area.
DisplayTitle:
push OpenFile
push ebx
call fopen
add esp, 8
cmp eax, 0
jne continue1
ret
DisplayBoard:
push OpenFile
push ebx
call fopen
add esp, 8
cmp eax, 0
jne continue2
ret
continue1:
mov ebx, eax
jmp readln1
continue2:
mov ebx, eax
jmp readln2
readln1:
push ebx
push DWORD TLENGTH
push tLENGTH
call fgets
add esp, 12
cmp eax, 0
jle done
push tLENGTH
call printf
add esp, 4
jmp readln1
readln2:
push ebx
push DWORD TLENGTH
push tLENGTH
call printf
add esp, 12
cmp eax, 0
jle done
jmp readln2
done:
push ebx
call fclose
add esp, 4
ret
;~.~. Procedures: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
; Place all your non-main procedure code in this area.
;~.~. The starting function: ~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
; this satisfies some compilers
; Place all your code for the main function in this area.
home:
ret ; for main instead of exit
;~_~_~ (end of file) ~_~_~_~_~_~_~_~_~_~_~_~_~_~_~_~_~_~_~_~_~_~_
I know that readln2 is wrong and that is were my error is, but I don't know how to read the file and display the ascii symbols.
Thanks for all the help and suggestions.
-
1.) Try using the "rb" mode with fopen.
2.) ASCII is text when you treat it as such. Read up how printf works, specifically how it can format things to be printed.
-
k, 'rb' doesn't help, but I did fix the run-on error in readln2. So it still just displays the title and the text? could it be because I am using the extern fgets to read in the file? I didn't mention it earlier, but I am using the ASCII & PC Extended Characters - Code Page 437
Here is the edited file
;
; Compiling this code for 32-bit use:
; nasm -f elf file.asm
;
;
;~.~. Definitions for readability: ~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
%define SYS_EXIT 1
%define SYS_READ 3
%define SYS_WRITE 4
%define STDIN 0
%define STDOUT 1
%define STDERR 2
;~.~. Initialized data: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
SECTION .data
Title: db 'title.txt', 0 ; Everything from title.txt
Board: db 'cBoard.txt', 0 ; Everything from cBoard.txt
OpenFile1: db 'r', 0 ; Opens an existing text file for reading
OpenFile2: db 'rb', 0
;~. Uninitialized data: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
SECTION .bss
TLENGTH EQU 72
tLENGTH resb TLENGTH
;~.~. Program code: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
SECTION .text
; Place all your extern declarations in this area.
extern fopen
extern fclose
extern fgets
extern printf
global main ; specify starting with main
main:
nop
xor ebx, ebx
mov ebx, Title
call DisplayTitle
xor ebx, ebx
mov ebx, Board
call DisplayBoard
jmp home
;~.~. Subroutines: ~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
; Place all your subroutine code in this area.
DisplayTitle:
push OpenFile1
push ebx
call fopen
add esp, 8
cmp eax, 0
jne continue1
ret
DisplayBoard:
push OpenFile2
push ebx
call fopen
add esp, 8
cmp eax, 0
jne continue2
ret
continue1:
mov ebx, eax
jmp readln1
continue2:
mov ebx, eax
jmp readln2
readln1:
push ebx
push DWORD TLENGTH
push tLENGTH
call fgets
add esp, 12
cmp eax, 0
jle done
push tLENGTH
call printf
add esp, 4
jmp readln1
readln2:
push ebx
push DWORD TLENGTH
push tLENGTH
call fgets
add esp, 12
cmp eax, 0
jle done
push tLENGTH
call printf
add esp, 4
jmp readln2
done:
push ebx
call fclose
add esp, 4
ret
;~.~. Procedures: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
; Place all your non-main procedure code in this area.
;~.~. The starting function: ~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
; this satisfies some compilers
; Place all your code for the main function in this area.
home:
ret ; for main instead of exit
;~_~_~ (end of file) ~_~_~_~_~_~_~_~_~_~_~_~_~_~_~_
-
I'm not sure I understand what you're trying to do. This is pretty screwed up, but may serve to clarify the question, "do you mean something like this?":
;
; Compiling this code for 32-bit use:
; nasm -f elf file.asm
;
;
;~.~. Definitions for readability: ~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
%define SYS_EXIT 1
%define SYS_READ 3
%define SYS_WRITE 4
%define STDIN 0
%define STDOUT 1
%define STDERR 2
;~.~. Initialized data: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
SECTION .data
Title: db 'title.txt', 0 ; Everything from title.txt
Board: db 'cBoard.txt', 0 ; Everything from cBoard.txt
OpenFile1: db 'r', 0 ; Opens an existing text file for reading
OpenFile2: db 'rb', 0
fmt_cx db `%c 0x%2X\n`, 0
;~. Uninitialized data: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
SECTION .bss
TLENGTH EQU 72
tLENGTH resb TLENGTH
;~.~. Program code: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
SECTION .text
; Place all your extern declarations in this area.
extern fopen
extern fclose
extern fgets
extern printf
global main ; specify starting with main
main:
nop
xor ebx, ebx
mov ebx, Title
call DisplayTitle
xor ebx, ebx
mov ebx, Board
call DisplayBoard
jmp home
;~.~. Subroutines: ~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
; Place all your subroutine code in this area.
DisplayTitle:
push OpenFile1
push ebx
call fopen
add esp, 8
cmp eax, 0
jne continue1
ret
DisplayBoard:
push OpenFile2
push ebx
call fopen
add esp, 8
cmp eax, 0
jne continue2
ret
continue1:
mov ebx, eax
jmp readln1
continue2:
mov ebx, eax
jmp readln2
readln1:
push ebx
push DWORD TLENGTH
push tLENGTH
call fgets
add esp, 12
cmp eax, 0
jle done
push tLENGTH
call printf
add esp, 4
jmp readln1
readln2:
push ebx
push DWORD TLENGTH
push tLENGTH
call fgets
add esp, 12
cmp eax, 0
jle done
mov esi, tLENGTH
.top:
movzx eax, byte [esi]
inc esi
test eax, eax
jz done
push eax
push eax
push fmt_cx
call printf
add esp, 4 * 3
jmp .top
; push tLENGTH
; call printf
; add esp, 4
; jmp readln2
done:
push ebx
call fclose
add esp, 4
ret
;~.~. Procedures: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
; Place all your non-main procedure code in this area.
;~.~. The starting function: ~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
; this satisfies some compilers
; Place all your code for the main function in this area.
home:
ret ; for main instead of exit
;~_~_~ (end of file) ~_~_~_~_~_~_~_~_~_~_~_~_~_~_~_
Best,
Frank
-
I am trying to read in these characters
201 205 203 205 203 205 203 205 203 205 203 205 203 205 203 205 187
186 177 186 224 186 177 186 224 186 177 186 224 186 177 186 224 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 224 186 177 186 224 186 177 186 224 186 177 186 224 186 177 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 177 186 224 186 177 186 224 186 177 186 224 186 177 186 224 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 177 186 32 186 177 186 32 186 177 186 32 186 177 186 32 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 32 186 177 186 32 186 177 186 32 186 177 186 32 186 177 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 225 186 177 186 225 186 177 186 225 186 177 186 225 186 177 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 177 186 225 186 177 186 225 186 177 186 225 186 177 186 225 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 225 186 177 186 225 186 177 186 225 186 177 186 225 186 177 186
200 205 202 205 202 205 202 205 202 205 202 205 202 205 202 205 188
the output is supposed to be this for the board is in the attatchment
-
This is the contents of the file you've attached
00000000 FF FE 54 25 50 25 66 25 50 25 66 25 50 25 66 25 50 25 66 25 50 25 66 25 ..T%P%f%P%f%P%f%P%f%P%f%
00000018 50 25 66 25 50 25 66 25 50 25 57 25 0D 00 0A 00 51 25 92 25 51 25 B1 03 P%f%P%f%P%W%....Q%.%Q%..
00000030 51 25 92 25 51 25 B1 03 51 25 92 25 51 25 B1 03 51 25 92 25 51 25 B1 03 Q%.%Q%..Q%.%Q%..Q%.%Q%..
00000048 51 25 0D 00 0A 00 60 25 50 25 6C 25 50 25 6C 25 50 25 6C 25 50 25 6C 25 Q%....`%P%l%P%l%P%l%P%l%
00000060 50 25 6C 25 50 25 6C 25 50 25 6C 25 50 25 63 25 0D 00 0A 00 51 25 B1 03 P%l%P%l%P%l%P%c%....Q%..
00000078 51 25 92 25 51 25 B1 03 51 25 92 25 51 25 B1 03 51 25 92 25 51 25 B1 03 Q%.%Q%..Q%.%Q%..Q%.%Q%..
so under no circumstances will you have any hope of achieving the results you expect in the previous post.
Secondly, "%c 0x%2X\n" is also inconsistent with your example.
-
I think the "%c 0x%2X\n" format was my idea... and apparently I was doing it "backwards". As you point out, the pasted numbers don't match "1234.txt". I think I'm still confused...
Best,
Frank
-
0xFFFE... smells like a Unicode byte order mark.
-
Yep, definitely Unicode.
An ASCII checkerboard with alphas and betas for pieces is somewhat amusing.
If I had to take a guess, I'd say someone copied the to-be-printed example into notepad and saved it as Unicode instead of ASCII.
Unless your instructor/instructions specifically state that you are to be working with Unicode, do the following at the command prompt (in the folder with 1234.txt) to get the right format.
type 1234.txt > 1234.ascii.txt
1234.ascii.txt should then have the desired ASCII format.
-
k, I think I am confused now too. What is in "1234.txt" is the desired result that is displayed when the file "cBoard.txt" is read in.
When I saved "1234.txt" I made the format as Unicode because it looked messy otherwise its just supposed to be a reference.
I am using the Code page 437 so everything in cBoard.txt should be the output as it is in "1234.txt"
So what is in "cBoard.txt" is the three-digit decimal form of the character number, from 000-255
and I am trying to get the character glyph to build the board
Meaning for example:
ASCII glyph
201 = ?
205 = ?
203 = ?
etc.
so everything read from cBoard.txt will appear on the screen similar to what is in 1234.txt.
my problem originally was when i was reading from the file it takes whats in the file and just displays whats in it. This is all good with the title, but when I read in the board its not and I don't know how to make the characters convert to the glyphs?
This is where I am at right now with the code
; Purpose: CSc475, Project Title
;
; Description: This code displays the Checkers title
;
; Compiling this code for 32-bit use:
; nasm -f elf file.asm
;
;
;~.~. Definitions for readability: ~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
%define SYS_EXIT 1
%define SYS_READ 3
%define SYS_WRITE 4
%define STDIN 0
%define STDOUT 1
%define STDERR 2
;~.~. Initialized data: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
SECTION .data
Title: db 'title.txt', 0 ; Everything from title.txt
Board: db 'cBoard.txt', 0 ; Everything from cBoard.txt
OpenFile1: db 'r', 0 ; Opens an existing text file for reading
OpenFile2: db 'r', 0
ASCIIFormat: db '%s', 0
;~. Uninitialized data: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
SECTION .bss
TLENGTH EQU 72
tLENGTH resb TLENGTH
;~.~. Program code: .~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
SECTION .text
; Place all your extern declarations in this area.
extern fopen
extern fclose
extern fgets
extern printf
global main ; specify starting with main
main:
nop
xor ebx, ebx ; set ebx to zero
mov ebx, Title ; move the title.txt to ebx
call DisplayTitle ; call DisplayTitle
xor ebx, ebx ; set ebx to zero
mov ebx, Board ; move the cBoard.txt to ebx
call DisplayBoard ; call DisplayBoard
jmp home ; jump to home
;~.~. Subroutines: ~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.~.
; Place all your subroutine code in this area.
DisplayTitle:
push OpenFile1 ; push address of open-for-read code "r"
push ebx ; address of the name of the file is in ebx
call fopen ; attempt to open the file for reading
add esp, 8 ; clean up stack
cmp eax, 0 ; fopen() returns null if attempted open failed
jne .continue ; jump if not equal to local label continue
ret ; return
.continue:
mov ebx, eax ; save handle of opened file in ebx
jmp .readln ; jump to local label readln
.readln:
push ebx ; push file handle on the stack
push DWORD TLENGTH ; limit line length of text read
push tLENGTH ; push address of the text in the file for buffer
call fgets ; read a line of text from the file
add esp, 12 ; clean stack
cmp eax, 0 ; a returned null indicates error or EOF
jle done ; if we get 0 in eax, close up and return
push tLENGTH ; push address of tLength on the stack
call printf ; call printf to display file
add esp, 4 ; clean stack
jmp .readln ; jump back to local label readln
DisplayBoard:
push OpenFile2 ; push address of open-for-read code "r"
push ebx ; address of the name of the file is in ebx
call fopen ; attempt to open the file for reading
add esp, 8 ; clean up stack
cmp eax, 0 ; fopen() returns null if attempted open failed
jne .continue ; jump if not equal to local label continue
ret ; return
.continue:
mov ebx, eax ; save handle of opened file in ebx
jmp .readln ; jump to local label readln
.readln:
push ebx ; push file handle on the stack
push DWORD TLENGTH ; limit line length of text read
push tLENGTH ; push address of the text in the file for buffer
; push ASCIIFormat ; was trying to make it be ASCII here?
call fgets ; read a line of text from the file
add esp, 12 ; clean stack
cmp eax, 0 ; a returned null indicates error or EOF
jle done ; if we get 0 in eax, close up and return
push tLENGTH ; push address of tLength on the stack
; push ASCIIFormat ; was trying to make it be ASCII here?
call printf ; call printf to display file
add esp, 4 ; clean stack
jmp .readln ; jump to local label readln
done:
push ebx
call fclose
add esp, 4
ret
home:
ret ; for main instead of exit
;~_~_~ (end of file) ~_~_~_~_~_~_~_~_~_~_
thanks and sorry for the confusion
-
ok so this forum doesn't actually display the ASCII Glyphs, but you can find the code page 437 at
http://en.wikipedia.org/wiki/Code_page_437 (http://en.wikipedia.org/wiki/Code_page_437)
-
As an encoding example, if I take the 8-bit ASCII character 0xC9 (the upper-left double-line corner symbol) and convert it to decimal form, I have the decimal number 201. However, ASCII is "binary" and decimal is not, so I have to use an intermediate representation form. Since I am already working with a universally accepted system such as ASCII, I can just store the number 201 in a file as the ASCII characters 0x32 0x30 0x31 in succession, and 201 is what you'll see when viewing the contents in a program such as notepad. Note that most hex editors illustrate this concept by having a binary/hexadecimal view and text view, side-by-side.
Now, if I wanted to make an assignment out of decoding a sequence of the above ASCII character encodings, how do you think you should go about doing that?
-
k, I brought it down to bare basic, no c call, just bare. This is how I am making the the ASCII glyph to display. I am actually hardcoding the hex value instead of the decimal value, and as a test it works. now how can I implement this from a file. like read it in and display it do I have to change the read mode to read and write mode because when I was using the call fgets I just got what was actually in the file no manipulation just displaying what was in the file.
section .data
msg db 0xc9,0xa
len equ $ - msg
section .bss
section .txt
global _start
_start:
mov edx,len
mov ecx,msg
mov ebx,1
mov eax,4
int 0x80
mov eax,1
int 0x80
-
Good plan, to go back to something simple and work back up. Do you see a "box-drawing" character? If you want to convince yourself that it doesn't matter how the numbers are represented, you could change it to:
msg db 201, 10
... should be exactly the same thing. (Nasm converts from the "text" in your source code to "numbers")
I saved the "pasted in" text from up above (not "1234.txt" which Keith identified as Unicode) as "cBoard.txt", and wrote a simple-minded routine to open it, read it, and convert from text to numbers, and print 'em as "ascii" (strictly speaking, "true ascii" is 7 bit code). Doesn't look like a "board" of any kind, but I think that's a "code page" issue. Comes out all on one line. My homemade "atoi", besides returning the number in eax (only al is interesting) also returns "pointer to next character" in edx, and the "invalid" (not a decimal digit) character that made it quit in ecx (cl). I think what I want to do is to ignore any spaces (which I do), but when a linefeed comes up, print it. Still won't look like a "board" but might be closer...
I should think that if you want to do it with C library calls, rather than read it with fgets, fscanf might work. I don't know how to get fscanf to skip the spaces (sometimes one, sometimes two) and perhaps the linefeeds. Maybe alternate fscanf and fgetc? I've always considered scanf to be "unfriendly", so I've never learned how to use it.
I can post my attempt, if you want, but it's really sloppy and needs to be cleaned up and commented. You seem to be on the right track...
Best,
Frank
-
Doesn't look like a "board" of any kind, but I think that's a "code page" issue. Comes out all on one line.
The original file had CRLF newlines, which I would imagine are supposed to indicate an implicit line break.
Read a line in, print that line out in ASCII form, CRLF, repeat.
-
CRLF? Well, I didn't do quite what you said, but same general effect, I think. Still doesn't look much like a "board". This is what I've got:
; nasm -f elf32 readboard.asm
; ld -o readboard readboard.o
global _start
section .data
board db "cBoard.txt", 0
section .bss
buffer resb 1000h
section .text
_start:
nop
mov ecx, 0
mov ebx, board
mov eax, 5
int 80h
test eax, eax
js exit
mov ebx, eax
mov edx, 1000h
mov ecx, buffer
mov eax, 3
int 80h
lea edi, [eax + ecx]
mov edx, buffer
.top:
push edx
call atoi
add esp, 4
cmp cl, 10
jnz .skipnl
mov al, 10
.skipnl:
call putc
cmp edx, edi
jnz .top
exit:
mov ebx, eax
mov eax, 1
int 80h
;--------------------
atoi:
push ebx
mov edx, [esp + 8] ; pointer to string
xor ebx, ebx ; assume not negative
cmp byte [edx], '-'
jnz notneg
inc ebx ; indicate negative
inc edx ; move past the '-'
notneg:
xor eax, eax ; clear "result"
.top:
movzx ecx, byte [edx]
inc edx
cmp ecx, byte '0'
jb .done
cmp ecx, byte '9'
ja .done
; we have a valid character - multiply
; result-so-far by 10, subtract '0'
; from the character to convert it to
; a number, and add it to result.
lea eax, [eax + eax * 4]
lea eax, [eax * 2 + ecx - 48]
jmp short .top
.done:
test ebx, ebx
jz notminus
neg eax
notminus:
pop ebx
ret
;------------------------
putc:
push edx
push ecx
push ebx
push eax
mov ecx, esp
mov edx, 1
mov ebx, 1
mov eax, 4
int 80h
pop eax
pop ebx
pop ecx
pop edx
ret
;-------------------
Told ya it was sloppy! :)
Best,
Frank
-
This:
201 205 203 205 203 205 203 205 203 205 203 205 203 205 203 205 187
186 177 186 224 186 177 186 224 186 177 186 224 186 177 186 224 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 224 186 177 186 224 186 177 186 224 186 177 186 224 186 177 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 177 186 224 186 177 186 224 186 177 186 224 186 177 186 224 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 32 186 177 186 32 186 177 186 32 186 177 186 32 186 177 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 177 186 32 186 177 186 32 186 177 186 32 186 177 186 32 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 225 186 177 186 225 186 177 186 225 186 177 186 225 186 177 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 177 186 225 186 177 186 225 186 177 186 225 186 177 186 225 186
204 205 206 205 206 205 206 205 206 205 206 205 206 205 206 205 185
186 225 186 177 186 225 186 177 186 225 186 177 186 225 186 177 186
200 205 202 205 202 205 202 205 202 205 202 205 202 205 202 205 188
... with this:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
FILE *fp = NULL;
char buffer[4096];
char tmp[4] = {0,0,0,0};
int cnt = 0;
void convert(void)
{
int c;
if(cnt > 0){
c = atoi((char *)&tmp);
if(c > 0) printf("%c",c);
memset((void *)tmp,0,4);
cnt = 0;
}
return;
}
int main(int argc, char *argv[])
{
int i,c,n;
fp = fopen("cBoard.txt","rb");
if(fp == NULL){
printf("Could not open cBoard.txt");
return 1;
}
while(!feof(fp)){
n = fread(buffer,1,4096,fp);
if((n == 0) || ((n != 4096) && ferror(fp))) break;
for(i=0; i<n; i++)
{
c = buffer[i];
if((c >= 0x30) && (c <= 0x39)){
tmp[cnt] = c;
cnt++;
if(cnt > 3) convert();
}else{
convert();
if((c == 0x0D) || (c == 0x0A)){
printf("%c",c);
}
}
}
}
convert();
fclose(fp);
return 0;
}
... or this:
global _main
extern _atoi
extern _printf
extern _fopen
extern _fread
extern _fclose
extern _feof
extern _ferror
extern _exit
[section .data]
file_name DB 'cBoard.txt',0
file_mode DB 'rb',0
file_handle DD 0
error_open DB 'Could not open cBoard.txt',0
char DB '%c',0
cnt DD 0
[section .bss]
tmp RESD 1
buffer RESB 4096
[section .text]
_main:
push file_mode
push file_name
call _fopen
add esp,8
mov DWORD[file_handle],eax
test eax,eax
jnz .read
push error_open
call _printf
add esp,4
jmp exit
.read:
call read
jc .last
mov edi,eax
mov esi,buffer
cld
.parse:
lodsb
cmp al,0x30
jb .whitespace
cmp al,0x39
ja .whitespace
mov ebx,tmp
add ebx,DWORD[cnt]
mov BYTE[ebx],al
inc DWORD[cnt]
cmp DWORD[cnt],3
jb .next
xor eax,eax
.whitespace:
push eax
call convert
pop eax
cmp al,0x0D
je .print
.linefeed:
cmp al,0x0A
jne .next
.print:
call print
.next:
dec edi
jnz .parse
jmp .read
.last:
call convert
exit:
mov eax,DWORD[file_handle]
test eax,eax
jz .ret
push eax
call _fclose
add esp,4
.ret:
xor eax,eax
ret
convert:
push tmp
call _atoi
add esp,4
test eax,eax
je .ret
call print
.ret:
mov DWORD[tmp],0
mov DWORD[cnt],0
ret
read:
push DWORD[file_handle]
call _feof
add esp,4
test eax,eax
jz .read
.eof:
stc
ret
.read:
push DWORD[file_handle]
push 4096
push 1
push buffer
call _fread
add esp,16
test eax,eax
jz .eof
cmp eax,4096
je .ret
push eax
push DWORD[file_handle]
call _ferror
add esp,4
mov ecx,eax
pop eax
test ecx,ecx
jnz .eof
.ret:
clc
ret
print:
movzx eax,al
push eax
push char
call _printf
add esp,8
ret
... produces this:
-
Well... I'm evidently doing something wrong. I still suspect a code page issue. From your C version. I get something quite similar to my simpleminded version, but with 17 characters per line (the CR?). Too lazy to pluck the underscores out of your .asm version at the moment (need an "--unprefix" option). Maybe later.
Best,
Frank
-
I still suspect a code page issue. From your C version.
Yep. Your version works under a Windows command prompt. Mine prints out garbled text within a Tiny Core Linux live cd terminal instance.
From what I can gather, you'll have to change the codepage to 437, or perhaps pipe the output through something like iconv.
All the more reason to use UTF-8 and not waste time with these silly types of issues :)
-
Wow, hey Keith do you mind if I implement your method into my program? I am wondering now how would I move the characters, alpha and beta? This is for a checkers game by the way guys. But with Keith's code I'm thinking that if I moved one of the alphas it would move all the alpha's? would I have to have another .txt file that corresponded to what alphas and betas they were say 1 was the first 2 was the next alpha, etc. ? or make an array of some sort? kinda lost there? or if I looked at it like a grid or made a grid where current selected alpha at (1, 2) could move to an appropriate position somewhere (?, ?). And then there is the movement question. I know that I can move the cursor, but I was kinda thinking that if I just made 2 parameters for destination and source of the checkers that that could maybe work. Any suggestions, tips, or anything. Thanks to all that have helped.
-
Keith where in the code do you actually find the 3 string of characters to convert. What variable are you saving them in?
-
k I found out that I can move the cursor with
Note: replace # with the number of rows to move.
§ represents the escape character, which is number 27 in the ASCII table
move cursor up §[#A
move cursor down §[#B
move cursor right §[#C
move cursor left §[#D
I'm still looking where you save the 3 string so that I might change the colors of them with
§[#m
Note: Replace # with:
30 for black
31 for red
32 for green
33 for yellow
34 for blue
35 for magenta
36 for cyan
37 for light gray
Thanks guys
-
Wow, hey Keith do you mind if I implement your method into my program?
Sure, but that's really a question for your instructor.
Keith where in the code do you actually find the 3 string of characters to convert. What variable are you saving them in?
Start at the end, the convert function, and work your way back.
Overall, I recommend taking the next step, and decoupling your presentation from your logic.