How many CPU operations programming languages use for % and fmod()? - operator-keyword

What is the result of C translation for % operator and fmod() function in machine language? What is it's implementation?
For example: Will 61199 % 256 be solved the same way as 61199 % 171?

If the platform supports integer division, like all modern non-embedded processors, it is a single instruction. The division instruction gives the quotient and the remainder.
Consider this C program (https://godbolt.org/z/vxj8fKdjG):
int main() {
int a = 61199;
int b = 171;
int c = a % b;
}
It compiles to:
main:
push rbp
mov rbp, rsp
mov DWORD PTR [rbp-4], 61199
mov DWORD PTR [rbp-8], 171
mov eax, DWORD PTR [rbp-4]
cdq
idiv DWORD PTR [rbp-8]
mov DWORD PTR [rbp-12], edx
mov eax, 0
pop rbp
ret
In this output idiv is the division instruction.

Related

Missing identifier name in WinDbg display

I'm inspecting a 64-bit executable using WinDbg(AMD64).
This is the assembly code that I'm assembling using ML64 to create my executable:
_data SEGMENT
b DWORD 0
a DWORD 0
_data ENDS
_text SEGMENT
main PROC
lea rax, a
mov dword ptr [rax], 1
lea rbx, b
mov dword ptr [rbx], 1
mov eax, dword ptr [rax]
add dword ptr [rbx], eax
inc eax
imul eax, dword ptr [rbx]
mov dword ptr [rbx], eax
ret
main ENDP
_text ENDS
END
And this is my ML64 command:
ml64.exe e:\Assembly\WindowsDebugging\PointersProject\PointersProject.asm /link /SUBSYSTEM:CONSOLE /ENTRY:main /DEBUG /OPT:NOREF,NOICF,NOLBR
All is well up to this point. But when I load this executable and disassemble the main function, the identifiers (a and b) are missing and I see <PERF> instead:
0:000> uf main
PointersProject!main:
00007ff7`b6211010 lea rax,[PointersProject!main <PERF> (PointersProject+0x4004) (00007ff7`b6214004)]
00007ff7`b6211017 mov dword ptr [rax],1
00007ff7`b621101d lea rbx,[PointersProject!main <PERF> (PointersProject+0x4000) (00007ff7`b6214000)]
00007ff7`b6211024 mov dword ptr [rbx],1
00007ff7`b621102a mov eax,dword ptr [rax]
00007ff7`b621102c add dword ptr [rbx],eax
00007ff7`b621102e inc eax
00007ff7`b6211030 imul eax,dword ptr [rbx]
00007ff7`b6211033 mov dword ptr [rbx],eax
00007ff7`b6211035 ret
I was expecting to see something like this instead for the LEA lines:
00000001`40001010 488d05ed2f0000 lea rax,[PointersProject!a (00000001`40004004)]
00000001`4000101d 488d1ddc2f0000 lea rbx,[PointersProject!b (00000001`40004000)]
What does <PERF> mean? Why is WinDbg not showing the identifiers ? Is it because of some optimization during the build process ? If so how do I avoid it ? Please help.

how can i print text in 16 bit real mode (graphical)?

i'm trying to write a boot sector that displays a small message on boot, but running the following on QEMU produces malformed text and any string with more than 5 characters doesn't show at all.
here's the code i assembled with NASM to a raw .bin file
[bits 16]
[org 0x7c00]
start:
xor ax,ax
mov ds,ax
mov es,ax
mov bx,0x8000
mov ax,0x13
int 0x10
mov ah,02
int 0x10
mov ah,0x02
mov bh,0x00
mov dh,0x12
mov dl,0x03
int 0x10
mov si , welcome
welcome db "hello",13,0
call RainbowPrint
RainbowPrint:
mov bl,1
mov ah, 0x0E
.repeat_next_char:
lodsb
cmp al, 0
je .done_print
add bl,6
int 0x10
jmp .repeat_next_char
.done_print:
ret
times (510 - ($ - $$)) db 0x00
dw 0xAA55
EDIT : here's an image showing the program running in qemu
You seem to overlapping your char_stream
welcome db "hello", 13, 0
I reviewed your code and came up with the following that has a clear display of your specific char_stream
[bits 16]
[org 0x7c00]
start:
xor ax,ax
mov ds,ax
mov es,ax
mov bx,0x8000
mov ax,0x13
int 0x10
mov ah,02
int 0x10
mov ah,0x02
mov bh,0x00
mov dh,0x12
mov dl,0x03
int 0x10
mov si , welcome
; Your [welcome] stream was here before...
call RainbowPrint
;***********
; Don't mind this area... just a simple key detection and reboot method...
xor ax, ax
int 0x16
xor ax, ax
int 0x19
;***********
; Move your stream away from operatable code areas:
welcome db "Hello, World!", 0x0D, 0x0A, 0x00
RainbowPrint:
mov bl,1
mov ah, 0x0E
.repeat_next_char:
lodsb
cmp al, 0
je .done_print
add bl,6
int 0x10
jmp .repeat_next_char
.done_print:
ret
times (510 - ($ - $$)) db 0x00
dw 0xAA55
The prefered text stream

Is it the code, or is it the OS..?

MY CODE IS
.model small
.data
arr db 83h, 12h, 0F0h, 0Bh, 89h
cnt db 05h
.code
mov ax, #data
mov ds, ax
mov si, offset arr
mov cl, cnt
sub bl, bl
sub dl, dl
back:
mov al, [si]
and al, 80h
jz skip
inc bl
skip:
inc dl
inc si
dec cl
jnz back
mov ah, 4cH
int 21H
end
THE ERRORS ARE AS FOLLOWS
1.asm:1: error: attempt to define a local label before any non-local labels
1.asm:1: error: parser: instruction expected
1.asm:2: error: attempt to define a local label before any non-local labels
1.asm:9: error: comma, colon, decorator or end of line expected after operand

Read a sector to address zero

%include "init.inc"
[org 0x0]
[bits 16]
jmp 0x07C0:start_boot
start_boot:
mov ax, cs
mov ds, ax
mov es, ax
load_setup:
mov ax, SETUP_SEG
mov es, ax
xor bx, bx
mov ah, 2 ; copy data to es:bx from disk.
mov al, 1 ; read a sector.
mov ch, 0 ; cylinder 0
mov cl, 2 ; read data since sector 2.
mov dh, 0 ; Head = 0
mov dl, 0 ; Drive = 0
int 0x13 ; BIOS call.
jc load_setup
lea si, [msg_load_setup]
call print
jmp $
print:
print_beg:
mov ax, 0xB800
mov es, ax
xor di, di
print_msg:
mov al, byte [si]
mov byte [es:di], al
or al, al
jz print_end
inc di
mov byte [es:di], BG_TEXT_COLOR
inc di
inc si
jmp print_msg
print_end:
ret
msg_load_setup db "Loading setup.bin was completed." , 0
times 510-($-$$) db 0
dw 0xAA55
I want to load setup.bin to memory address zero. So, I input 0 value to es register (SETUP_SEG = 0). bx, too. But it didn't work. then, I have a question about this issue. My test is below.
SETUP_SEG's value
0x0000 : fail
0x0010 : success
0x0020 : fail
0x0030 : fail
0x0040 : fail
0x0050 : success
I can't understand why this situation was happened. All test was carried out on VMware. Does anyone have an idea ?
I'm not sure if this is your problem, but your trying to load setup.bin in the Real Mode IVT (Interrupt Vector Table). The IVT contains the location of each interrupt, so I'm assuming that your boatloader is overwriting them when it loads setup.bin into memory! Interrupts can be sneaky and tricky, since they can be called even if you didn't call them. Any interrupt vector you overwrote will likely cause undefined behavior when called, which will cause some problems.
I suggest setting SETUP_SEG to a higher number like 0x2000 or 0x3000, but the lowest you could safely go is 0x07E0. The Osdev Wiki and Wikipedia have some helpful information on conventional memory and memory mapping.
I hope this helps!

Assembly printing system date

I have a problem with printing system date because of cx register size. How can it be solved without any big changes?
title casadatum
zas segment stack
db 256 dup(?)
zas ends
strsize EQU 64
dat segment
print db 'Current System Date is : $'
date db 'dd:mm:rrrr$'
nl db 10,13,'$'
dat ends
code segment
assume cs:code, ss:zas, ds:dat
get_date proc
mov ah,2ah
int 21h
mov al,dl
call convert
mov [bx],ax
mov al,dh
call convert
mov [bx+3],ax
mov al,cx
call convert
mov [bx+6],ax
ret
endp
convert proc
push dx
mov ah,0
mov dl,10
div dl
or ax, 3030h
pop dx
ret
endp
start:
mov ax, seg dat
mov ds,ax
LEA BX, date
CALL GET_date
lea dx,print
mov ah,09h
int 21h
lea dx,date
mov ah,09h
int 21h
koniec:
mov ah, 4ch
int 21h
code ends
end start
Replace this part of your code
mov al,cx
call convert
mov [bx+6],ax
with these instructions
mov al,100
xchg ax,cx
div cl
mov ch,ah
call convert
mov [bx+6],ax
mov al,ch
call convert
mov [bx+8],ax