4 Commits

Author SHA1 Message Date
9cf6ecc535 feat: done first task 2024-12-10 18:06:59 +03:00
34ed7f9fcc fix: first time assembles 2024-12-08 20:13:47 +03:00
08ae2e64c9 fixed nasm 2024-12-08 19:34:29 +03:00
009f4d3bda feat: mvp 2024-12-08 19:14:13 +03:00
8 changed files with 1272 additions and 77 deletions

View File

@ -1,7 +0,0 @@
obj-m += task1.o
modules:
make -C /lib/modules/$(shell uname -r)/build M=$(PWD) modules
clean:
make -C /lib/modules/$(shell uname -r)/build M=$(PWD) clean

View File

@ -1,22 +0,0 @@
!_TAG_FILE_FORMAT 2 /extended format; --format=1 will not append ;" to lines/
!_TAG_FILE_SORTED 1 /0=unsorted, 1=sorted, 2=foldcase/
!_TAG_OUTPUT_EXCMD mixed /number, pattern, mixed, or combineV2/
!_TAG_OUTPUT_FILESEP slash /slash or backslash/
!_TAG_OUTPUT_MODE u-ctags /u-ctags or e-ctags/
!_TAG_PATTERN_LENGTH_LIMIT 96 /0 for no limit/
!_TAG_PROC_CWD /home/electronixtm/code/CA/09-keyboard/ //
!_TAG_PROGRAM_AUTHOR Universal Ctags Team //
!_TAG_PROGRAM_NAME Universal Ctags /Derived from Exuberant Ctags/
!_TAG_PROGRAM_URL https://ctags.io/ /official site/
!_TAG_PROGRAM_VERSION 5.9.0 //
IDT_rebuild task1.c /^static int __init IDT_rebuild(void)$/;" f typeref:typename:int __init file:
IDT_restore task1.c /^static void __exit IDT_restore(void)$/;" f typeref:typename:void __exit file:
INCLUDE_VERMAGIC task1.mod.c /^#define INCLUDE_VERMAGIC$/;" d file:
____versions task1.mod.c /^static const struct modversion_info ____versions[]$/;" v typeref:typename:const struct modversion_info[]__used __section ("__versions") file:
clean Makefile /^clean: $/;" t
global test.asm /^global interrupt_wrapper$/;" l
interrupt_wrapper test.asm /^interrupt_wrapper:$/;" l
kern_page task1.c /^static u64 kern_page; \/\/ u64 - macro meaning unsigned 64 bits$/;" v typeref:typename:u64 file:
modules Makefile /^modules:$/;" t
Лабораторная работа 9 README.md /^# Лабораторная работа 9$/;" c
Обмен ЭВМ с клавиатурой README.md /^## Обмен ЭВМ с клавиатурой$/;" s chapter:Лабораторная работа 9

View File

@ -1,43 +0,0 @@
#include<linux/module.h>
#include<linux/printk.h>
#include<linux/mm.h>
#include<asm/desc.h>
#include<linux/kernel.h>
#include<asm/traps.h>
static u64 kern_page; // u64 - macro meaning unsigned 64 bits
static gate
static struct desc_ptr default_idtr; // to save existing idtr
static int __init IDT_rebuild(void)
{
struct desc_ptr idtr; // here we're going to store our new interupts table
pr_info("---IDT-REBUILD INITIATED---");
store_idt(&default_idtr); // getting current idtr and store it
pr_info("obtained idtr");
pr_info("allocating new memory page");
kern_page = __get_free_page(GFP_KERNEL);
if (!kern_page)
{
return -ENOMEM;
}
idtr.address = kern_page; // going to store
idtr.size = default_idtr.size;
return 0;
}
static void __exit IDT_restore(void)
{
struct desc_ptr idtr;
store_idt(&idtr);
if (idtr.address != default_idtr.address || idtr.size != default_idtr.size)
{
load_idt(&default_idtr);
free_page(kern_page);
}
}
module_init(IDT_rebuild);
module_exit(IDT_restore);
MODULE_LICENSE("GPL");

View File

@ -1,5 +0,0 @@
global interrupt_wrapper
section .text
interrupt_wrapper:

379
coursework/main.asm Normal file
View File

@ -0,0 +1,379 @@
global _start
%define NAME_SIZE 64
%define BUFF_SIZE 1024
section .bss
name resb NAME_SIZE
buffer resb BUFF_SIZE
section .data
buffer_tail dq buffer
iseof db 0
;strings
E_open_file db `Something went wrong while opening file\n`
section .text
read:
push rcx
push r11
mov rax, 0
syscall
pop r11
pop rcx
ret
write:
push rcx
push r11
mov rax, 1
syscall
pop r11
pop rcx
ret
namecmp:
.LFB6:
push rbp
mov rbp, rsp
mov -8[rbp], rdi
mov -16[rbp], rsi
jmp .L2
.L6:
mov rax, -8[rbp]
movzx edx, BYTE [rax]
mov rax, -16[rbp]
movzx eax, BYTE [rax]
cmp dl, al
je .L3
mov eax, 0
jmp .L4
.L3:
add QWORD -8[rbp], 1
add QWORD -16[rbp], 1
.L2:
mov rax, -8[rbp]
movzx eax, BYTE [rax]
test al, al
je .L5
mov rax, -16[rbp]
movzx eax, BYTE [rax]
test al, al
jne .L6
.L5:
mov eax, 1
.L4:
pop rbp
ret
openfile:
push rbp
mov rbp, rsp
sub rsp, 32
mov -24[rbp], rdi
mov rax, -24[rbp]
mov esi, 0
mov rdi, rax
mov eax, 2
syscall
mov -4[rbp], eax
cmp DWORD -4[rbp], 0
jns .L8
mov rdi, 1
mov rsi, E_open_file
mov rdx, 40
call write
mov edi, 1
mov rax, 60
mov rdi, 1
syscall
.L8:
mov eax, -4[rbp]
leave
ret
fill_buffer:
push rbp
mov rbp, rsp
sub rsp, 32
mov -20[rbp], edi
mov rdx, [buffer_tail]
lea rax, [buffer]
sub rdx, rax
mov eax, 1024
sub rax, rdx
mov -8[rbp], rax
mov rdx, -8[rbp]
mov eax, -20[rbp]
lea rcx, [buffer]
mov rsi, rcx
mov edi, eax
call read
mov -16[rbp], rax
cmp QWORD -16[rbp], 1023
ja .L11
mov BYTE [iseof], 1
.L11:
lea rdx, [buffer]
mov rax, -16[rbp]
add rax, rdx
mov [buffer_tail], rax
nop
leave
ret
find_second_word:
push rbp
mov rbp, rsp
mov -8[rbp], rdi
jmp .L13
.L14:
add QWORD -8[rbp], 1
.L13:
mov rax, -8[rbp]
movzx eax, BYTE [rax]
cmp al, 32
jne .L14
add QWORD -8[rbp], 1
mov rax, -8[rbp]
pop rbp
ret
find_fullname_end:
push rbp
mov rbp, rsp
lea rax, [buffer]
mov -8[rbp], rax
jmp .L17
.L20:
add QWORD -8[rbp], 1
.L17:
mov rax, -8[rbp]
movzx eax, BYTE [rax]
cmp al, 10
jne .L18
mov rax, -8[rbp]
movzx eax, BYTE [rax]
test al, al
jne .L19
.L18:
lea rax, [buffer+1024]
cmp -8[rbp], rax
jb .L20
.L19:
lea rax, [buffer+1024]
cmp -8[rbp], rax
jne .L21
mov eax, 0
jmp .L22
.L21:
mov rax, -8[rbp]
.L22:
pop rbp
ret
pop_fullname:
push rbp
mov rbp, rsp
sub rsp, 32
mov eax, 0
call find_fullname_end
add rax, 1
mov -16[rbp], rax
lea rdx, [buffer]
mov rax, -16[rbp]
sub rax, rdx
mov -24[rbp], rax
mov QWORD -8[rbp], 0
jmp .L24
.L25:
mov rdx, -16[rbp]
mov rax, -8[rbp]
add rax, rdx
movzx eax, BYTE [rax]
lea rcx, [buffer]
mov rdx, -8[rbp]
add rdx, rcx
mov BYTE [rdx], al
mov rdx, -16[rbp]
mov rax, -8[rbp]
add rax, rdx
mov BYTE [rax], 0
add QWORD -8[rbp], 1
.L24:
mov eax, 1024
sub rax, -24[rbp]
cmp -8[rbp], rax
jb .L25
mov rax, [buffer_tail]
mov rdx, -24[rbp]
neg rdx
add rax, rdx
mov [buffer_tail], rax
nop
leave
ret
preprint db `count: `
postprint db `\n`
print_count:
push rbp
mov rbp, rsp
sub rsp, 32
mov -24[rbp], rdi
mov edx, 8
mov rax, preprint
mov rsi, rax
mov edi, 1
call write
jmp .L27
.L28:
mov rcx, -24[rbp]
mov rdx, -3689348814741910323
mov rax, rcx
mul rdx
shr rdx, 3
mov rax, rdx
sal rax, 2
add rax, rdx
add rax, rax
sub rcx, rax
mov rdx, rcx
mov eax, edx
add eax, 48
mov BYTE -1[rbp], al
mov rax, -24[rbp]
mov rdx, -3689348814741910323
mul rdx
mov rax, rdx
shr rax, 3
mov -24[rbp], rax
lea rax, -1[rbp]
mov edx, 1
mov rsi, rax
mov edi, 1
call write
.L27:
cmp QWORD -24[rbp], 0
jne .L28
mov edx, 1
mov rax, postprint
mov rsi, rax
mov edi, 1
call write
nop
leave
ret
get_name:
push rbp
mov rbp, rsp
sub rsp, 40
mov -40[rbp], rdi
lea rax, [buffer]
mov rdi, rax
call find_second_word
mov -24[rbp], rax
mov rax, -24[rbp]
mov -8[rbp], rax
jmp .L30
.L31:
add QWORD -8[rbp], 1
.L30:
mov rax, -8[rbp]
movzx eax, BYTE [rax]
cmp al, 32
jne .L31
cmp QWORD -8[rbp], 0
jne .L32
mov eax, -1
jmp .L33
.L32:
mov QWORD -16[rbp], 0
jmp .L34
.L35:
mov rdx, -24[rbp]
mov rax, -16[rbp]
add rax, rdx
mov rcx, -40[rbp]
mov rdx, -16[rbp]
add rdx, rcx
movzx eax, BYTE [rax]
mov BYTE [rdx], al
add QWORD -16[rbp], 1
.L34:
mov rdx, -24[rbp]
mov rax, -16[rbp]
add rax, rdx
cmp rax, -8[rbp]
jb .L35
mov eax, 0
.L33:
leave
ret
_start:
push rbp
mov rbp, rsp
sub rsp, 96
mov -84[rbp], edi
mov -96[rbp], rsi
mov rax, -96[rbp]
add rax, 8
mov rax, [rax]
mov rdi, rax
call openfile
mov -12[rbp], eax
mov edx, 64
lea rax, [name]
mov rsi, rax
mov edi, 0
call read
mov QWORD -8[rbp], 0
mov QWORD -80[rbp], 0
mov QWORD -72[rbp], 0
mov QWORD -64[rbp], 0
mov QWORD -56[rbp], 0
mov QWORD -48[rbp], 0
mov QWORD -40[rbp], 0
mov QWORD -32[rbp], 0
mov QWORD -24[rbp], 0
.L39:
mov eax, 0
call find_fullname_end
test rax, rax
jne .L37
mov eax, DWORD -12[rbp]
mov edi, eax
call fill_buffer
.L37:
lea rax, -80[rbp]
mov rdi, rax
call get_name
lea rax, -80[rbp]
lea rdx, [name]
mov rsi, rdx
mov rdi, rax
call namecmp
test eax, eax
je .L38
add QWORD -8[rbp], 1
.L38:
mov eax, 0
call pop_fullname
mov rdx, [buffer_tail]
lea rax, [buffer]
cmp rdx, rax
jne .L39
mov rax, -8[rbp]
mov rdi, rax
call print_count
mov eax, 0
leave
ret

134
coursework/main.c Normal file
View File

@ -0,0 +1,134 @@
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#define BUFF_SIZE 1024
#define NAME_SIZE 64
#define STDIN 0
#define STDOUT 1
typedef unsigned long long u64;
char name[NAME_SIZE];
char buffer[BUFF_SIZE];
char* buffer_tail = buffer; // points on first free symbol
char iseof = 0;
int namecmp(char* name1, char* name2)
{
for (; *name1 && *name2; name1++, name2++)
{
if (*name1 != *name2)
{
return 0;
}
}
return 1;
}
int openfile(char* filename)
{
int file = open(filename, O_RDONLY);
if (file < 0)
{
puts("Something went wrong while opening file\n");
exit(1);
}
return file;
}
void fill_buffer(int filedesc)
{
const size_t tofill = BUFF_SIZE - (buffer_tail - buffer);
u64 bytes_read = read(filedesc, buffer, tofill);
if (bytes_read < BUFF_SIZE)
{
iseof = 1;
}
buffer_tail = buffer + bytes_read;
}
char* find_second_word(char* start)
{
for (; *start != ' '; start++);
return ++start;
}
char* find_fullname_end()
{
char* end = buffer;
for (; (*end != '\n' || *end == 0)
&& end < buffer + BUFF_SIZE; end++);
if (end == buffer + BUFF_SIZE)
{
return NULL;
}
return end;
}
void pop_fullname() // pops from buffer
{
char* end = find_fullname_end() + 1;
u64 fullname_len = end - buffer;
size_t i = 0;
for (; i < BUFF_SIZE - fullname_len; i++)
{
buffer[i] = end[i];
end[i] = 0;
}
buffer_tail -= fullname_len;
}
void print_count(u64 count)
{
write(STDOUT, "count: ", 8);
while (count)
{
char digit = (count % 10) + '0';
count /= 10;
write(STDOUT, &digit, 1);
}
write(STDOUT, "\n", 1);
}
int get_name(char* accumulator)
{
char* start = find_second_word(buffer);
char* end = start;
for (; *end != ' '; end++);
if (!end)
{
return -1;
}
for (size_t i = 0; &start[i] < end; i++)
{
accumulator[i] = start[i];
}
return 0;
}
int main(int argc, char* argv[])
{
int filedesc = openfile(argv[1]);
read(STDIN, name, sizeof(name)/sizeof(name[0]));
// fgets(name, sizeof(name)/sizeof(name[0]), stdin);
size_t count = 0;
char namebuff[NAME_SIZE] = {0, };
do
{
if (!find_fullname_end())
{
fill_buffer(filedesc);
}
get_name(namebuff);
if (namecmp(namebuff, name))
{
count++;
}
pop_fullname();
} while (buffer_tail != buffer);
print_count(count);
return 0;
}

467
coursework/main.s Normal file
View File

@ -0,0 +1,467 @@
.file "main.c"
.intel_syntax noprefix
.text
.globl name
.bss
.align 32
.type name, @object
.size name, 64
name:
.zero 64
.globl buffer
.align 32
.type buffer, @object
.size buffer, 1024
buffer:
.zero 1024
.globl buffer_tail
.section .data.rel.local,"aw"
.align 8
.type buffer_tail, @object
.size buffer_tail, 8
buffer_tail:
.quad buffer
.globl iseof
.bss
.type iseof, @object
.size iseof, 1
iseof:
.zero 1
.text
.globl namecmp
.type namecmp, @function
namecmp:
.LFB6:
.cfi_startproc
push rbp
.cfi_def_cfa_offset 16
.cfi_offset 6, -16
mov rbp, rsp
.cfi_def_cfa_register 6
mov QWORD PTR -8[rbp], rdi
mov QWORD PTR -16[rbp], rsi
jmp .L2
.L6:
mov rax, QWORD PTR -8[rbp]
movzx edx, BYTE PTR [rax]
mov rax, QWORD PTR -16[rbp]
movzx eax, BYTE PTR [rax]
cmp dl, al
je .L3
mov eax, 0
jmp .L4
.L3:
add QWORD PTR -8[rbp], 1
add QWORD PTR -16[rbp], 1
.L2:
mov rax, QWORD PTR -8[rbp]
movzx eax, BYTE PTR [rax]
test al, al
je .L5
mov rax, QWORD PTR -16[rbp]
movzx eax, BYTE PTR [rax]
test al, al
jne .L6
.L5:
mov eax, 1
.L4:
pop rbp
.cfi_def_cfa 7, 8
ret
.cfi_endproc
.LFE6:
.size namecmp, .-namecmp
.section .rodata
.align 8
.LC0:
.string "Something went wrong while opening file\n"
.text
.globl openfile
.type openfile, @function
openfile:
.LFB7:
.cfi_startproc
push rbp
.cfi_def_cfa_offset 16
.cfi_offset 6, -16
mov rbp, rsp
.cfi_def_cfa_register 6
sub rsp, 32
mov QWORD PTR -24[rbp], rdi
mov rax, QWORD PTR -24[rbp]
mov esi, 0
mov rdi, rax
mov eax, 0
call open@PLT
mov DWORD PTR -4[rbp], eax
cmp DWORD PTR -4[rbp], 0
jns .L8
lea rax, .LC0[rip]
mov rdi, rax
call puts@PLT
mov edi, 1
call exit@PLT
.L8:
mov eax, DWORD PTR -4[rbp]
leave
.cfi_def_cfa 7, 8
ret
.cfi_endproc
.LFE7:
.size openfile, .-openfile
.globl fill_buffer
.type fill_buffer, @function
fill_buffer:
.LFB8:
.cfi_startproc
push rbp
.cfi_def_cfa_offset 16
.cfi_offset 6, -16
mov rbp, rsp
.cfi_def_cfa_register 6
sub rsp, 32
mov DWORD PTR -20[rbp], edi
mov rdx, QWORD PTR buffer_tail[rip]
lea rax, buffer[rip]
sub rdx, rax
mov eax, 1024
sub rax, rdx
mov QWORD PTR -8[rbp], rax
mov rdx, QWORD PTR -8[rbp]
mov eax, DWORD PTR -20[rbp]
lea rcx, buffer[rip]
mov rsi, rcx
mov edi, eax
call read@PLT
mov QWORD PTR -16[rbp], rax
cmp QWORD PTR -16[rbp], 1023
ja .L11
mov BYTE PTR iseof[rip], 1
.L11:
lea rdx, buffer[rip]
mov rax, QWORD PTR -16[rbp]
add rax, rdx
mov QWORD PTR buffer_tail[rip], rax
nop
leave
.cfi_def_cfa 7, 8
ret
.cfi_endproc
.LFE8:
.size fill_buffer, .-fill_buffer
.globl find_second_word
.type find_second_word, @function
find_second_word:
.LFB9:
.cfi_startproc
push rbp
.cfi_def_cfa_offset 16
.cfi_offset 6, -16
mov rbp, rsp
.cfi_def_cfa_register 6
mov QWORD PTR -8[rbp], rdi
jmp .L13
.L14:
add QWORD PTR -8[rbp], 1
.L13:
mov rax, QWORD PTR -8[rbp]
movzx eax, BYTE PTR [rax]
cmp al, 32
jne .L14
add QWORD PTR -8[rbp], 1
mov rax, QWORD PTR -8[rbp]
pop rbp
.cfi_def_cfa 7, 8
ret
.cfi_endproc
.LFE9:
.size find_second_word, .-find_second_word
.globl find_fullname_end
.type find_fullname_end, @function
find_fullname_end:
.LFB10:
.cfi_startproc
push rbp
.cfi_def_cfa_offset 16
.cfi_offset 6, -16
mov rbp, rsp
.cfi_def_cfa_register 6
lea rax, buffer[rip]
mov QWORD PTR -8[rbp], rax
jmp .L17
.L20:
add QWORD PTR -8[rbp], 1
.L17:
mov rax, QWORD PTR -8[rbp]
movzx eax, BYTE PTR [rax]
cmp al, 10
jne .L18
mov rax, QWORD PTR -8[rbp]
movzx eax, BYTE PTR [rax]
test al, al
jne .L19
.L18:
lea rax, buffer[rip+1024]
cmp QWORD PTR -8[rbp], rax
jb .L20
.L19:
lea rax, buffer[rip+1024]
cmp QWORD PTR -8[rbp], rax
jne .L21
mov eax, 0
jmp .L22
.L21:
mov rax, QWORD PTR -8[rbp]
.L22:
pop rbp
.cfi_def_cfa 7, 8
ret
.cfi_endproc
.LFE10:
.size find_fullname_end, .-find_fullname_end
.globl pop_fullname
.type pop_fullname, @function
pop_fullname:
.LFB11:
.cfi_startproc
push rbp
.cfi_def_cfa_offset 16
.cfi_offset 6, -16
mov rbp, rsp
.cfi_def_cfa_register 6
sub rsp, 32
mov eax, 0
call find_fullname_end
add rax, 1
mov QWORD PTR -16[rbp], rax
lea rdx, buffer[rip]
mov rax, QWORD PTR -16[rbp]
sub rax, rdx
mov QWORD PTR -24[rbp], rax
mov QWORD PTR -8[rbp], 0
jmp .L24
.L25:
mov rdx, QWORD PTR -16[rbp]
mov rax, QWORD PTR -8[rbp]
add rax, rdx
movzx eax, BYTE PTR [rax]
lea rcx, buffer[rip]
mov rdx, QWORD PTR -8[rbp]
add rdx, rcx
mov BYTE PTR [rdx], al
mov rdx, QWORD PTR -16[rbp]
mov rax, QWORD PTR -8[rbp]
add rax, rdx
mov BYTE PTR [rax], 0
add QWORD PTR -8[rbp], 1
.L24:
mov eax, 1024
sub rax, QWORD PTR -24[rbp]
cmp QWORD PTR -8[rbp], rax
jb .L25
mov rax, QWORD PTR buffer_tail[rip]
mov rdx, QWORD PTR -24[rbp]
neg rdx
add rax, rdx
mov QWORD PTR buffer_tail[rip], rax
nop
leave
.cfi_def_cfa 7, 8
ret
.cfi_endproc
.LFE11:
.size pop_fullname, .-pop_fullname
.section .rodata
.LC1:
.string "count: "
.LC2:
.string "\n"
.text
.globl print_count
.type print_count, @function
print_count:
.LFB12:
.cfi_startproc
push rbp
.cfi_def_cfa_offset 16
.cfi_offset 6, -16
mov rbp, rsp
.cfi_def_cfa_register 6
sub rsp, 32
mov QWORD PTR -24[rbp], rdi
mov edx, 8
lea rax, .LC1[rip]
mov rsi, rax
mov edi, 1
call write@PLT
jmp .L27
.L28:
mov rcx, QWORD PTR -24[rbp]
movabs rdx, -3689348814741910323
mov rax, rcx
mul rdx
shr rdx, 3
mov rax, rdx
sal rax, 2
add rax, rdx
add rax, rax
sub rcx, rax
mov rdx, rcx
mov eax, edx
add eax, 48
mov BYTE PTR -1[rbp], al
mov rax, QWORD PTR -24[rbp]
movabs rdx, -3689348814741910323
mul rdx
mov rax, rdx
shr rax, 3
mov QWORD PTR -24[rbp], rax
lea rax, -1[rbp]
mov edx, 1
mov rsi, rax
mov edi, 1
call write@PLT
.L27:
cmp QWORD PTR -24[rbp], 0
jne .L28
mov edx, 1
lea rax, .LC2[rip]
mov rsi, rax
mov edi, 1
call write@PLT
nop
leave
.cfi_def_cfa 7, 8
ret
.cfi_endproc
.LFE12:
.size print_count, .-print_count
.globl get_name
.type get_name, @function
get_name:
.LFB13:
.cfi_startproc
push rbp
.cfi_def_cfa_offset 16
.cfi_offset 6, -16
mov rbp, rsp
.cfi_def_cfa_register 6
sub rsp, 40
mov QWORD PTR -40[rbp], rdi
lea rax, buffer[rip]
mov rdi, rax
call find_second_word
mov QWORD PTR -24[rbp], rax
mov rax, QWORD PTR -24[rbp]
mov QWORD PTR -8[rbp], rax
jmp .L30
.L31:
add QWORD PTR -8[rbp], 1
.L30:
mov rax, QWORD PTR -8[rbp]
movzx eax, BYTE PTR [rax]
cmp al, 32
jne .L31
cmp QWORD PTR -8[rbp], 0
jne .L32
mov eax, -1
jmp .L33
.L32:
mov QWORD PTR -16[rbp], 0
jmp .L34
.L35:
mov rdx, QWORD PTR -24[rbp]
mov rax, QWORD PTR -16[rbp]
add rax, rdx
mov rcx, QWORD PTR -40[rbp]
mov rdx, QWORD PTR -16[rbp]
add rdx, rcx
movzx eax, BYTE PTR [rax]
mov BYTE PTR [rdx], al
add QWORD PTR -16[rbp], 1
.L34:
mov rdx, QWORD PTR -24[rbp]
mov rax, QWORD PTR -16[rbp]
add rax, rdx
cmp rax, QWORD PTR -8[rbp]
jb .L35
mov eax, 0
.L33:
leave
.cfi_def_cfa 7, 8
ret
.cfi_endproc
.LFE13:
.size get_name, .-get_name
.globl main
.type main, @function
main:
.LFB14:
.cfi_startproc
push rbp
.cfi_def_cfa_offset 16
.cfi_offset 6, -16
mov rbp, rsp
.cfi_def_cfa_register 6
sub rsp, 96
mov DWORD PTR -84[rbp], edi
mov QWORD PTR -96[rbp], rsi
mov rax, QWORD PTR -96[rbp]
add rax, 8
mov rax, QWORD PTR [rax]
mov rdi, rax
call openfile
mov DWORD PTR -12[rbp], eax
mov edx, 64
lea rax, name[rip]
mov rsi, rax
mov edi, 0
call read@PLT
mov QWORD PTR -8[rbp], 0
mov QWORD PTR -80[rbp], 0
mov QWORD PTR -72[rbp], 0
mov QWORD PTR -64[rbp], 0
mov QWORD PTR -56[rbp], 0
mov QWORD PTR -48[rbp], 0
mov QWORD PTR -40[rbp], 0
mov QWORD PTR -32[rbp], 0
mov QWORD PTR -24[rbp], 0
.L39:
mov eax, 0
call find_fullname_end
test rax, rax
jne .L37
mov eax, DWORD PTR -12[rbp]
mov edi, eax
call fill_buffer
.L37:
lea rax, -80[rbp]
mov rdi, rax
call get_name
lea rax, -80[rbp]
lea rdx, name[rip]
mov rsi, rdx
mov rdi, rax
call namecmp
test eax, eax
je .L38
add QWORD PTR -8[rbp], 1
.L38:
mov eax, 0
call pop_fullname
mov rdx, QWORD PTR buffer_tail[rip]
lea rax, buffer[rip]
cmp rdx, rax
jne .L39
mov rax, QWORD PTR -8[rbp]
mov rdi, rax
call print_count
mov eax, 0
leave
.cfi_def_cfa 7, 8
ret
.cfi_endproc
.LFE14:
.size main, .-main
.ident "GCC: (Debian 14.2.0-6) 14.2.0"
.section .note.GNU-stack,"",@progbits

292
coursework/old/main.asm Normal file
View File

@ -0,0 +1,292 @@
global _start
%define STDIN 0
%define STDOUT 1
%define STDERR 2
%define RD_ONLY 00
%define FILE_BUF_SIZE 1024
section .data
buffer_tail_ptr dq file_buffer ; stores pointer to the end of the buffer for file
is_eof db 0 ; indicates if file ended
count dq 0 ; сколько имен нашлось
section .bss
name resb 128
real_name_len resb 1
name_size equ $-name
file_descriptor resq 1
file_buffer resb FILE_BUF_SIZE
section .text
%macro PRINT_STR 1
jmp %%run ; we define data right in code. It's not good, but ok for prototype
%%string db %1
%%string_len equ $-%%string
%%run:
mov rax, 1
mov rdi, STDOUT
mov rsi, %%string
mov rdx, %%string_len
syscall
%endmacro
%macro MPUSH 1-*
%rep %0
push %1
%rotate 1
%endrep
%endmacro
%macro MPOP_R 1-*
%rotate -1
%rep %0
pop %1
%rotate -1
%endrep
%endmacro
is_alpha: ; dl - symbol in ascii
xor al, al
cmp dl, 'A'
jl .exit
cmp dl, 'z'
jg .exit
; dl < 'Z' or dl > 'a'
cmp dl, 'Z'
jl .true
cmp dl, 'a'
jg .true
jmp .exit
.true:
mov al, 1
.exit:
ret
fill_buf: ; read bytes from file to buffer
MPUSH rdi, rsi, rcx, r11, rdx
mov rdi, [buffer_tail_ptr]
call buffer_left
mov rdx, rax
mov rax, 0
mov rdi, [file_descriptor]
mov rsi, [buffer_tail_ptr]
; mov rdx, FILE_BUF_SIZE
syscall
cmp rax, 0
jl file_read_error
add [buffer_tail_ptr], rax
cmp rax, FILE_BUF_SIZE
jg .exit
mov byte [is_eof], 1
.exit:
MPOP_R rdi, rsi, rcx, r11, rdx
ret
read_name: ; ask user for name he is searching for
MPUSH rax, rdi, rsi, rdx, rcx
mov rax, 0
mov rdi, STDIN
mov rsi, name
mov rdx, name_size
syscall ; returns number of read bytes
cmp rax, 0
jl read_error
test rax, rax
jz no_name_error ; if no bytes were read
mov [real_name_len], al
; if user didn't end output with CTRL+D, there will be one extra symbol
mov dl, [name + rax - 1]
call is_alpha ; check if last symbol is alpha
test al, al
jnz .exit
; if last symbol is \n or something simmilar, erase it
xor rdx, rdx
mov dl, byte [real_name_len]
mov byte [name + rdx - 1], 0 ; clear last char if non alpha
dec byte [real_name_len]
.exit:
MPOP_R rax, rdi, rsi, rdx, rcx
ret
are_names_equal: ; takes first fullname from buff and compares
MPUSH rcx, rsi, rdi
; jump to second word
mov rdi, file_buffer
mov rcx, FILE_BUF_SIZE
mov al, ' '
repne scasb ; Теперь мы указываем на символ второго слова
mov r8, rdi ; store for later
repne scasb ; Ищем второй пробел, чтобы определить границы второго слова
dec rdi ; Нашелся второй пробел. убавляем 1 чтобы указывать именно на него
sub rdi, r8 ; len
mov rax, rdi
cmp al, [real_name_len]
jnz .false ; if lenghts are different - already false
mov rdi, r8 ; return to pointer on second word
mov rsi, name
xor rcx, rcx
mov cl, [real_name_len]
repe cmpsb
jnz .false
.true:
mov rax, 1
jmp .exit
.false:
mov rax, 0
.exit:
MPOP_R rcx, rsi ,rdi
ret
buffer_left: ; counts free part of buffer
push rdi
mov rax, FILE_BUF_SIZE
sub rdi, file_buffer
sub rax, rdi
pop rdi
ret
pop_from_addr: ; frees buffer from one name until \n, takes 1 addr
push rbp
mov rbp, rsp
MPUSH rdx, rax
sub rsp, 24
mov [rbp-24], rdi ; char* start
call buffer_left
mov [rbp-16], rax ; * count
mov QWORD [rbp-8], 0 ; i
;loop
.loop:
; read byte from start[i]
mov rdx, [rbp-24]
mov rax, [rbp-8]
add rax, rdx
mov al, [rax]
; place to buffer[i]
mov rdx, [rbp-8]
add rdx, file_buffer
mov [rdx], al
; move zero to read position
mov rdx, [rbp-24]
mov rax, [rbp-8]
add rax, rdx
mov byte [rax], 0
inc qword [rbp-8]
; .cond:
mov rax, [rbp-8]
cmp rax, [rbp-16]
jb .loop
; update buffer_tail_ptr
mov rax, [rbp-24]
sub rax, file_buffer
sub [buffer_tail_ptr], rax
add rsp, 24
MPOP_R rcx, rax
pop rbp
ret
free_fullname:
MPUSH rcx, rdi, rax
mov rcx, FILE_BUF_SIZE
mov rdi, file_buffer
mov al, `\n`
repne scasb
call pop_from_addr
MPOP_R rcx, rdi, rax
ret
_start:
; --parse command_line arguments
push rbp
mov rbp, rsp
; --check if there is any args
mov rax, [rbp + 8]
cmp rax, 2
jl no_filepath
; --if argument specified, try to read path
mov rdi, [rbp + 8*3]
mov rax, 0x2 ; open file
mov rsi, RD_ONLY
xor rdx, rdx
syscall ; filepath already should be in rdi
mov [file_descriptor], rax
cmp rax, 0
jl file_open_error
; --asking user what name we are looking for
PRINT_STR `Input name you are looking for: `
call read_name
; -- find number of occurenses. HARDEST PART
.fill_buff_prefix:
call fill_buf
.name_cmp_loop:
mov rdi, name
call are_names_equal
test rax, rax
jz .no_increment
inc qword [count]
.no_increment:
call free_fullname
; iseof && buffer_tail_ptr == file_buffer
mov rax, [buffer_tail_ptr]
cmp rax, file_buffer
jne .name_cmp_loop
mov al, [is_eof]
test al, al
jz .fill_buff_prefix
;formatted output
mov rax, 1 ; write
mov rdi, STDOUT
mov rsi, name
mov rdx, [real_name_len]
syscall
PRINT_STR " ............... "
; printing number
mov rax, [count]
mov rbx, 10
xor rcx, rcx
.number_converting_loop:
xor rdx, rdx
div rbx
; push 1 byte to stack
add dl, '0' ; convert to ascii
dec rsp
mov [rsp], dl
inc rcx
test rax, rax
jnz .number_converting_loop
mov rax, 1
mov rdi, STDOUT
mov rsi, rsp
mov rdx, rcx
syscall
PRINT_STR `\n`
jmp exit
read_error:
PRINT_STR `Error while reading the name\n`
jmp exit
no_name_error:
PRINT_STR `No propper name given\n`
jmp exit
file_open_error:
PRINT_STR `Failed to open the file\n`
jmp exit
file_read_error:
PRINT_STR `Error while reading the file\n`
jmp exit
no_filepath:
PRINT_STR `You haven't specified a file to read from\n`
jmp exit
exit:
mov rax, 60
mov rdi, 0
syscall