├── Makefile ├── README.md ├── boot ├── README.md └── boot.asm ├── build.sh ├── cpu ├── README.md ├── gdt.c ├── gdt.h ├── idt.c ├── idt.h ├── interrupt.asm ├── irq.c ├── irq.h ├── kb.c ├── kb.h ├── timer.c └── timer.h ├── include ├── README.md ├── about.h ├── input.h ├── ports.c ├── ports.h ├── print.c ├── print.h ├── string.c └── string.h ├── kernel.bin ├── kernel ├── README.md ├── kernel.c └── loader.asm ├── link.ld ├── screenshot.png └── user ├── shell ├── README.md ├── shell.c └── shell.h └── taskbar ├── README.md ├── taskbar.c └── taskbar.h /Makefile: -------------------------------------------------------------------------------- 1 | C_SOURCES = $(wildcard kernel/*.c include/*.c cpu/*.c) 2 | HEADERS = $(wildcard kernel/*.h include/*.h cpu/*.h) 3 | 4 | 5 | loader: 6 | nasm -f elf32 -o loader.o kernel/loader.asm 7 | nasm -f elf32 -o cpu/interrupt.o cpu/interrupt.asm 8 | 9 | kern: 10 | gcc -m32 -g -ffreestanding -c include/print.c -o include/print.o 11 | gcc -m32 -g -ffreestanding -c include/ports.c -o include/ports.o 12 | gcc -m32 -g -ffreestanding -c include/string.c -o include/string.o 13 | gcc -m32 -g -ffreestanding -c cpu/idt.c -o cpu/idt.o 14 | gcc -m32 -g -ffreestanding -c cpu/irq.c -o cpu/irq.o 15 | gcc -m32 -g -ffreestanding -c cpu/timer.c -o cpu/timer.o 16 | gcc -m32 -g -ffreestanding -c cpu/kb.c -o cpu/kb.o 17 | gcc -m32 -g -ffreestanding -c user/shell/shell.c -o user/shell/shell.o 18 | gcc -m32 -g -ffreestanding -c user/taskbar/taskbar.c -o user/taskbar/taskbar.o 19 | gcc -m32 -g -ffreestanding -c kernel/kernel.c -o main.o 20 | 21 | link: 22 | ld -m elf_i386 -Ttext 0x1000 -o kernel.bin loader.o main.o $(wildcard include/*.o cpu/*.o user/shell/*.o user/taskbar/*.o) 23 | 24 | run: 25 | qemu-system-x86_64 -kernel kernel.bin 26 | clean: 27 | rm *.o include/*.o cpu/*.o user/shell/*.o user/taskbar/*.o 28 | 29 | all:loader kern link clean run 30 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Simple-Operating-System-from-Scratch 2 | A simple operating system build from scratch using C and assembly language. 3 | The code includes a make file that will help you to run this whole program. 4 | 5 | | ![ScreenShot](screenshot.png) | 6 | | :--: | 7 | | *Main window of the mini-operating system* | 8 | 9 | 10 | ## Requirements 11 | 1. nasm 12 | 2. gcc 13 | 3. ld 14 | 4. qemu-system-x86_64 15 | 16 | ## Command to run 17 | $ make all 18 | -------------------------------------------------------------------------------- /boot/README.md: -------------------------------------------------------------------------------- 1 | # Bootloader files 2 | -------------------------------------------------------------------------------- /boot/boot.asm: -------------------------------------------------------------------------------- 1 | [bits 16] 2 | [org 0x7c00] 3 | 4 | global _start 5 | 6 | _start: 7 | mov ax, 0 8 | mov ss, ax 9 | mov bp, 0x9000 10 | mov sp, bp 11 | 12 | jmp 0:loader 13 | 14 | gdt_start: 15 | dd 0x0 16 | dd 0x0 17 | 18 | gdt_code: 19 | dw 0xffff 20 | dw 0x0 21 | db 0x0 22 | db 10011010b 23 | db 11001111b 24 | db 0x0 25 | 26 | gdt_data: 27 | dw 0xffff 28 | dw 0x0 29 | db 0x0 30 | db 10010010b 31 | db 11001111b 32 | db 0x0 33 | 34 | gdt_end: 35 | 36 | gdt_desc: 37 | dw gdt_end-gdt_start-1 38 | dd gdt_start 39 | 40 | CODE_SEG equ gdt_code-gdt_start 41 | DATA_SEG equ gdt_data-gdt_start 42 | 43 | print: 44 | pusha 45 | mov ah, 0x0e 46 | repeat: 47 | mov al, [bx] 48 | cmp al, 0 49 | je done 50 | int 0x10 51 | add bx, 1 52 | jmp repeat 53 | done: 54 | popa 55 | ret 56 | 57 | MSG db "welcome to bootloader",13,10,0 58 | PROT db "loading protected mode",13,10,0 59 | ERR db "Error in reading disk",13,10,0 60 | 61 | error: 62 | mov bx, ERR 63 | call print 64 | jmp disk_loop 65 | disk_loop: 66 | jmp $ 67 | 68 | loader: 69 | mov ax, 0 70 | mov ds, ax 71 | mov es, ax 72 | mov fs, ax 73 | mov gs, ax 74 | 75 | mov ah, 0x06 76 | mov al, 0 77 | int 0x10 78 | mov ah, 0x00 79 | mov al, 7h 80 | int 0x10 81 | 82 | mov bx, MSG 83 | call print 84 | 85 | mov bx, 0x1000 86 | 87 | mov ah, 0x2 88 | mov al, 0x2 89 | mov cl, 0x2 90 | mov ch, 0x0 91 | mov dh, 0x0 92 | int 0x13 93 | jc error 94 | jnc switch_pm 95 | 96 | switch_pm: 97 | xor ax, ax 98 | mov ds, ax 99 | cli 100 | lgdt[gdt_desc] 101 | mov eax, cr0 102 | or eax, 0x1 103 | mov cr0, eax 104 | jmp CODE_SEG:init_pm 105 | 106 | [bits 32] 107 | 108 | VIDEO_MEMORY equ 0xb8000 109 | WHITE_ON_BLACK equ 0x0f 110 | 111 | print_pm: 112 | pusha 113 | mov edx, VIDEO_MEMORY 114 | loop_pm: 115 | mov al, [ebx] 116 | mov ah, WHITE_ON_BLACK 117 | cmp al, 0 118 | je done_pm 119 | mov [edx], ax 120 | add ebx, 1 121 | add edx, 2 122 | jmp loop_pm 123 | done_pm: 124 | popa 125 | ret 126 | 127 | init_pm: 128 | mov ax, DATA_SEG 129 | mov ds, ax 130 | mov es, ax 131 | mov fs, ax 132 | mov gs, ax 133 | mov ss, ax 134 | 135 | mov ebp, 0x9000 136 | mov esp, ebp 137 | 138 | mov ebx, PROT 139 | call print_pm 140 | 141 | jmp $ 142 | 143 | times 510-($-$$) db 0 144 | dw 0xAA55 145 | -------------------------------------------------------------------------------- /build.sh: -------------------------------------------------------------------------------- 1 | 2 | nasm -f bin boot/boot.asm -o boot.bin 3 | 4 | nasm -f elf32 kernel/loader.asm -o loader.o 5 | 6 | gcc -m32 -c kernel/kernel.c -o kernel.o 7 | 8 | ld -Ttext 0x1000 -o kernel.bin loader.o kernel.o 9 | 10 | cat boot.bin kernel.bin > os.bin 11 | 12 | rm *.o 13 | qemu-system-x86_64 -kernel kernel.bin 14 | #grub-mkrescue -o os.iso os/ 15 | 16 | -------------------------------------------------------------------------------- /cpu/README.md: -------------------------------------------------------------------------------- 1 | # CPU files 2 | -------------------------------------------------------------------------------- /cpu/gdt.c: -------------------------------------------------------------------------------- 1 | #include "gdt.h" 2 | #define GDT_LEN 5 3 | 4 | static gdt_entry gdt[GDT_LEN]; 5 | static gdt_ptr gdt_p; 6 | 7 | static void gdt_desc(gdt_entry desc, unsigned int base, unsigned int limit, unsigned char access, unsigned char granularity){ 8 | desc.base_low=(base & 0xFFFF); 9 | desc.base_middle=(base >> 16) && 0xFF; 10 | desc.base_high=(base >> 24) & 0xFF; 11 | desc.limit_low=(limit & 0xFFFF); 12 | desc.granularity=((limit >> 16) & 0x0F) | (granularity & 0xF0); 13 | desc.access=access; 14 | 15 | gdt_p.base=(unsigned int)&gdt; 16 | gdt_p.limit = sizeof(gdt_entry) * GDT_LEN - 1; 17 | 18 | load_gdt(&gdt_p); 19 | } 20 | 21 | void gdt_install(){ 22 | gdt_desc(gdt[0], 0, 0, 0, 0); // null 23 | gdt_desc(gdt[1], 0, 0xFFFFFFFF, 0x9A, 0xCF); // ring0 code 24 | gdt_desc(gdt[2], 0, 0xFFFFFFFF, 0x92, 0xCF); // ring0 data 25 | gdt_desc(gdt[3], 0, 0xFFFFFFFF, 0xFA, 0xCF); // ring3 code 26 | gdt_desc(gdt[4], 0, 0xFFFFFFFF, 0xF2, 0xCF); // ring3 data 27 | } 28 | -------------------------------------------------------------------------------- /cpu/gdt.h: -------------------------------------------------------------------------------- 1 | #ifndef __GDT_H__ 2 | #define __GDT_H__ 3 | 4 | typedef struct{ 5 | unsigned short limit_low; 6 | unsigned short base_low; 7 | unsigned char base_middle; 8 | unsigned char access; 9 | unsigned char granularity; 10 | unsigned char base_high; 11 | }__attribute__((packed)) gdt_entry; 12 | 13 | typedef struct{ 14 | unsigned short limit; 15 | unsigned int base; 16 | }__attribute__((packed)) gdt_ptr; 17 | 18 | #endif 19 | -------------------------------------------------------------------------------- /cpu/idt.c: -------------------------------------------------------------------------------- 1 | #include "idt.h" 2 | 3 | struct idt_entry idt[256]; 4 | struct idt_ptr idt_p; 5 | 6 | void idt_desc(int n, unsigned long base){ 7 | idt[n].low_offset=low_16(base); 8 | idt[n].sel=KERNEL_CS; 9 | idt[n].zero=0; 10 | idt[n].flags=IDT_FLAGS; 11 | idt[n].high_offset=high_16(base); 12 | } 13 | 14 | void set_idt(){ 15 | idt_p.limit=(sizeof(struct idt_entry)*256)-1; 16 | idt_p.base=(unsigned long)&idt; 17 | load_idt(&idt_p); 18 | }; 19 | -------------------------------------------------------------------------------- /cpu/idt.h: -------------------------------------------------------------------------------- 1 | #ifndef __IDT_H__ 2 | #define __IDT_H__ 3 | 4 | #define low_16(address) (unsigned short)((address) & 0xFFFF) 5 | #define high_16(address) (unsigned short)(((address) >> 16) & 0xFFFF) 6 | 7 | #define KERNEL_CS 0x08 8 | #define IDT_FLAGS 0x8E 9 | 10 | struct idt_entry{ 11 | unsigned short low_offset; 12 | unsigned short sel; 13 | unsigned char zero; 14 | unsigned char flags; 15 | unsigned short high_offset; 16 | }__attribute__((packed)); 17 | 18 | struct idt_ptr{ 19 | unsigned short limit; 20 | unsigned long base; 21 | }__attribute__((packed)); 22 | 23 | void idt_desc(int n, unsigned long base); 24 | void set_idt(); 25 | 26 | #endif 27 | -------------------------------------------------------------------------------- /cpu/interrupt.asm: -------------------------------------------------------------------------------- 1 | 2 | [extern isr_handler] 3 | [extern irq_handler] 4 | 5 | 6 | isr_common_stub: 7 | pusha 8 | mov ax, ds 9 | push eax 10 | mov ax, 0x10 11 | mov ds, ax 12 | mov es, ax 13 | mov fs, ax 14 | mov gs, ax 15 | 16 | call isr_handler 17 | 18 | pop eax 19 | mov ds, ax 20 | mov es, ax 21 | mov fs, ax 22 | mov gs, ax 23 | popa 24 | add esp, 8 25 | sti 26 | iret 27 | 28 | irq_common_stub: 29 | pusha 30 | mov ax, ds 31 | push eax 32 | mov ax, 0x10 33 | mov ds, ax 34 | mov es, ax 35 | mov fs, ax 36 | mov gs, ax 37 | 38 | call irq_handler 39 | 40 | pop ebx 41 | mov ds, bx 42 | mov es, bx 43 | mov fs, bx 44 | mov gs, bx 45 | popa 46 | add esp, 8 47 | sti 48 | iret 49 | 50 | global isr0 51 | global isr1 52 | global isr2 53 | global isr3 54 | global isr4 55 | global isr5 56 | global isr6 57 | global isr7 58 | global isr8 59 | global isr9 60 | global isr10 61 | global isr11 62 | global isr12 63 | global isr13 64 | global isr14 65 | global isr15 66 | global isr16 67 | global isr17 68 | global isr18 69 | global isr19 70 | global isr20 71 | global isr21 72 | global isr22 73 | global isr23 74 | global isr24 75 | global isr25 76 | global isr26 77 | global isr27 78 | global isr28 79 | global isr29 80 | global isr30 81 | global isr31 82 | 83 | global irq0 84 | global irq1 85 | global irq2 86 | global irq3 87 | global irq4 88 | global irq5 89 | global irq6 90 | global irq7 91 | global irq8 92 | global irq9 93 | global irq10 94 | global irq11 95 | global irq12 96 | global irq13 97 | global irq14 98 | global irq15 99 | 100 | ; 0: Divide By Zero Exception 101 | isr0: 102 | cli 103 | push byte 0 104 | push byte 0 105 | jmp isr_common_stub 106 | 107 | ; 1: Debug Exception 108 | isr1: 109 | cli 110 | push byte 0 111 | push byte 1 112 | jmp isr_common_stub 113 | 114 | ; 2: Non Maskable Interrupt Exception 115 | isr2: 116 | cli 117 | push byte 0 118 | push byte 2 119 | jmp isr_common_stub 120 | 121 | ; 3: Int 3 Exception 122 | isr3: 123 | cli 124 | push byte 0 125 | push byte 3 126 | jmp isr_common_stub 127 | 128 | ; 4: INTO Exception 129 | isr4: 130 | cli 131 | push byte 0 132 | push byte 4 133 | jmp isr_common_stub 134 | 135 | ; 5: Out of Bounds Exception 136 | isr5: 137 | cli 138 | push byte 0 139 | push byte 5 140 | jmp isr_common_stub 141 | 142 | ; 6: Invalid Opcode Exception 143 | isr6: 144 | cli 145 | push byte 0 146 | push byte 6 147 | jmp isr_common_stub 148 | 149 | ; 7: Coprocessor Not Available Exception 150 | isr7: 151 | cli 152 | push byte 0 153 | push byte 7 154 | jmp isr_common_stub 155 | 156 | ; 8: Double Fault Exception (With Error Code!) 157 | isr8: 158 | cli 159 | push byte 8 160 | jmp isr_common_stub 161 | 162 | ; 9: Coprocessor Segment Overrun Exception 163 | isr9: 164 | cli 165 | push byte 0 166 | push byte 9 167 | jmp isr_common_stub 168 | 169 | ; 10: Bad TSS Exception (With Error Code!) 170 | isr10: 171 | cli 172 | push byte 10 173 | jmp isr_common_stub 174 | 175 | ; 11: Segment Not Present Exception (With Error Code!) 176 | isr11: 177 | cli 178 | push byte 11 179 | jmp isr_common_stub 180 | 181 | ; 12: Stack Fault Exception (With Error Code!) 182 | isr12: 183 | cli 184 | push byte 12 185 | jmp isr_common_stub 186 | 187 | ; 13: General Protection Fault Exception (With Error Code!) 188 | isr13: 189 | cli 190 | push byte 13 191 | jmp isr_common_stub 192 | 193 | ; 14: Page Fault Exception (With Error Code!) 194 | isr14: 195 | cli 196 | push byte 14 197 | jmp isr_common_stub 198 | 199 | ; 15: Reserved Exception 200 | isr15: 201 | cli 202 | push byte 0 203 | push byte 15 204 | jmp isr_common_stub 205 | 206 | ; 16: Floating Point Exception 207 | isr16: 208 | cli 209 | push byte 0 210 | push byte 16 211 | jmp isr_common_stub 212 | 213 | ; 17: Alignment Check Exception 214 | isr17: 215 | cli 216 | push byte 0 217 | push byte 17 218 | jmp isr_common_stub 219 | 220 | ; 18: Machine Check Exception 221 | isr18: 222 | cli 223 | push byte 0 224 | push byte 18 225 | jmp isr_common_stub 226 | 227 | ; 19: Reserved 228 | isr19: 229 | cli 230 | push byte 0 231 | push byte 19 232 | jmp isr_common_stub 233 | 234 | ; 20: Reserved 235 | isr20: 236 | cli 237 | push byte 0 238 | push byte 20 239 | jmp isr_common_stub 240 | 241 | ; 21: Reserved 242 | isr21: 243 | cli 244 | push byte 0 245 | push byte 21 246 | jmp isr_common_stub 247 | 248 | ; 22: Reserved 249 | isr22: 250 | cli 251 | push byte 0 252 | push byte 22 253 | jmp isr_common_stub 254 | 255 | ; 23: Reserved 256 | isr23: 257 | cli 258 | push byte 0 259 | push byte 23 260 | jmp isr_common_stub 261 | 262 | ; 24: Reserved 263 | isr24: 264 | cli 265 | push byte 0 266 | push byte 24 267 | jmp isr_common_stub 268 | 269 | ; 25: Reserved 270 | isr25: 271 | cli 272 | push byte 0 273 | push byte 25 274 | jmp isr_common_stub 275 | 276 | ; 26: Reserved 277 | isr26: 278 | cli 279 | push byte 0 280 | push byte 26 281 | jmp isr_common_stub 282 | 283 | ; 27: Reserved 284 | isr27: 285 | cli 286 | push byte 0 287 | push byte 27 288 | jmp isr_common_stub 289 | 290 | ; 28: Reserved 291 | isr28: 292 | cli 293 | push byte 0 294 | push byte 28 295 | jmp isr_common_stub 296 | 297 | ; 29: Reserved 298 | isr29: 299 | cli 300 | push byte 0 301 | push byte 29 302 | jmp isr_common_stub 303 | 304 | ; 30: Reserved 305 | isr30: 306 | cli 307 | push byte 0 308 | push byte 30 309 | jmp isr_common_stub 310 | 311 | ; 31: Reserved 312 | isr31: 313 | cli 314 | push byte 0 315 | push byte 31 316 | jmp isr_common_stub 317 | 318 | ; IRQ handlers 319 | irq0: 320 | cli 321 | push byte 0 322 | push byte 32 323 | jmp irq_common_stub 324 | 325 | irq1: 326 | cli 327 | push byte 1 328 | push byte 33 329 | jmp irq_common_stub 330 | 331 | irq2: 332 | cli 333 | push byte 2 334 | push byte 34 335 | jmp irq_common_stub 336 | 337 | irq3: 338 | cli 339 | push byte 3 340 | push byte 35 341 | jmp irq_common_stub 342 | 343 | irq4: 344 | cli 345 | push byte 4 346 | push byte 36 347 | jmp irq_common_stub 348 | 349 | irq5: 350 | cli 351 | push byte 5 352 | push byte 37 353 | jmp irq_common_stub 354 | 355 | irq6: 356 | cli 357 | push byte 6 358 | push byte 38 359 | jmp irq_common_stub 360 | 361 | irq7: 362 | cli 363 | push byte 7 364 | push byte 39 365 | jmp irq_common_stub 366 | 367 | irq8: 368 | cli 369 | push byte 8 370 | push byte 40 371 | jmp irq_common_stub 372 | 373 | irq9: 374 | cli 375 | push byte 9 376 | push byte 41 377 | jmp irq_common_stub 378 | 379 | irq10: 380 | cli 381 | push byte 10 382 | push byte 42 383 | jmp irq_common_stub 384 | 385 | irq11: 386 | cli 387 | push byte 11 388 | push byte 43 389 | jmp irq_common_stub 390 | 391 | irq12: 392 | cli 393 | push byte 12 394 | push byte 44 395 | jmp irq_common_stub 396 | 397 | irq13: 398 | cli 399 | push byte 13 400 | push byte 45 401 | jmp irq_common_stub 402 | 403 | irq14: 404 | cli 405 | push byte 14 406 | push byte 46 407 | jmp irq_common_stub 408 | 409 | irq15: 410 | cli 411 | push byte 15 412 | push byte 47 413 | jmp irq_common_stub 414 | 415 | -------------------------------------------------------------------------------- /cpu/irq.c: -------------------------------------------------------------------------------- 1 | #include "irq.h" 2 | #include "idt.h" 3 | #include "../include/print.h" 4 | #include "../include/ports.h" 5 | #include "../include/string.h" 6 | 7 | void irq_install(){ 8 | idt_desc(0, (unsigned int)isr0); 9 | idt_desc(1, (unsigned int)isr1); 10 | idt_desc(2, (unsigned int)isr2); 11 | idt_desc(3, (unsigned int)isr3); 12 | idt_desc(4, (unsigned int)isr4); 13 | idt_desc(5, (unsigned int)isr5); 14 | idt_desc(6, (unsigned int)isr6); 15 | idt_desc(7, (unsigned int)isr7); 16 | idt_desc(8, (unsigned int)isr8); 17 | idt_desc(9, (unsigned int)isr9); 18 | idt_desc(10, (unsigned int)isr10); 19 | idt_desc(11, (unsigned int)isr11); 20 | idt_desc(12, (unsigned int)isr12); 21 | idt_desc(13, (unsigned int)isr13); 22 | idt_desc(14, (unsigned int)isr14); 23 | idt_desc(15, (unsigned int)isr15); 24 | idt_desc(16, (unsigned int)isr16); 25 | idt_desc(17, (unsigned int)isr17); 26 | idt_desc(18, (unsigned int)isr18); 27 | idt_desc(19, (unsigned int)isr19); 28 | idt_desc(20, (unsigned int)isr20); 29 | idt_desc(21, (unsigned int)isr21); 30 | idt_desc(22, (unsigned int)isr22); 31 | idt_desc(23, (unsigned int)isr23); 32 | idt_desc(24, (unsigned int)isr24); 33 | idt_desc(25, (unsigned int)isr25); 34 | idt_desc(26, (unsigned int)isr26); 35 | idt_desc(27, (unsigned int)isr27); 36 | idt_desc(28, (unsigned int)isr28); 37 | idt_desc(29, (unsigned int)isr29); 38 | idt_desc(30, (unsigned int)isr30); 39 | idt_desc(31, (unsigned int)isr31); 40 | 41 | outb(0x20, 0x11); 42 | outb(0xA0, 0x11); 43 | outb(0x21, 0x20); 44 | outb(0xA1, 0x28); 45 | outb(0x21, 0x04); 46 | outb(0xA1, 0x02); 47 | outb(0x21, 0x01); 48 | outb(0xA1, 0x01); 49 | outb(0x21, 0x0); 50 | outb(0xA1, 0x0); 51 | 52 | idt_desc(32, (unsigned int)irq0); 53 | idt_desc(33, (unsigned int)irq1); 54 | idt_desc(34, (unsigned int)irq2); 55 | idt_desc(35, (unsigned int)irq3); 56 | idt_desc(36, (unsigned int)irq4); 57 | idt_desc(37, (unsigned int)irq5); 58 | idt_desc(38, (unsigned int)irq6); 59 | idt_desc(39, (unsigned int)irq7); 60 | idt_desc(40, (unsigned int)irq8); 61 | idt_desc(41, (unsigned int)irq9); 62 | idt_desc(42, (unsigned int)irq10); 63 | idt_desc(43, (unsigned int)irq11); 64 | idt_desc(44, (unsigned int)irq12); 65 | idt_desc(45, (unsigned int)irq13); 66 | idt_desc(46, (unsigned int)irq14); 67 | idt_desc(47, (unsigned int)irq15); 68 | 69 | set_idt(); 70 | } 71 | 72 | char* exception[]={ 73 | "Division By Zero", 74 | "Debug", 75 | "Non Maskable Interrupt", 76 | "Breakpoint", 77 | "Into Detected Overflow", 78 | "Out of Bounds", 79 | "Invalid Opcode", 80 | "No Coprocessor", 81 | 82 | "Double Fault", 83 | "Coprocessor Segment Overrun", 84 | "Bad TSS", 85 | "Segment Not Present", 86 | "Stack Fault", 87 | "General Protection Fault", 88 | "Page Fault", 89 | "Unknown Interrupt", 90 | 91 | "Coprocessor Fault", 92 | "Alignment Check", 93 | "Machine Check", 94 | "Reserved", 95 | "Reserved", 96 | "Reserved", 97 | "Reserved", 98 | "Reserved", 99 | 100 | "Reserved", 101 | "Reserved", 102 | "Reserved", 103 | "Reserved", 104 | "Reserved", 105 | "Reserved", 106 | "Reserved", 107 | "Reserved" 108 | 109 | }; 110 | 111 | isr_t interrupt_handlers[256]; 112 | 113 | void isr_handler(struct regs r){ 114 | print("\nInterrupt Encountered: "); 115 | char s[3]; 116 | int_to_ascii(r.int_no, s); 117 | print(s); 118 | print("\n"); 119 | print(exception[r.int_no]); 120 | print("\n"); 121 | } 122 | 123 | void irq_install_handlers(unsigned char n, isr_t handler) { 124 | interrupt_handlers[n] = handler; 125 | } 126 | 127 | void irq_handler(struct regs r){ 128 | 129 | if (r.int_no >= 40) outb(0xA0, 0x20); 130 | outb(0x20, 0x20); 131 | if (interrupt_handlers[r.int_no] != 0) { 132 | isr_t handler = interrupt_handlers[r.int_no]; 133 | handler(r); 134 | } 135 | } 136 | 137 | 138 | -------------------------------------------------------------------------------- /cpu/irq.h: -------------------------------------------------------------------------------- 1 | #ifndef __IRQ_H__ 2 | #define __IRQ_H__ 3 | 4 | extern void isr0(); 5 | extern void isr1(); 6 | extern void isr2(); 7 | extern void isr3(); 8 | extern void isr4(); 9 | extern void isr5(); 10 | extern void isr6(); 11 | extern void isr7(); 12 | extern void isr8(); 13 | extern void isr9(); 14 | extern void isr10(); 15 | extern void isr11(); 16 | extern void isr12(); 17 | extern void isr13(); 18 | extern void isr14(); 19 | extern void isr15(); 20 | extern void isr16(); 21 | extern void isr17(); 22 | extern void isr18(); 23 | extern void isr19(); 24 | extern void isr20(); 25 | extern void isr21(); 26 | extern void isr22(); 27 | extern void isr23(); 28 | extern void isr24(); 29 | extern void isr25(); 30 | extern void isr26(); 31 | extern void isr27(); 32 | extern void isr28(); 33 | extern void isr29(); 34 | extern void isr30(); 35 | extern void isr31(); 36 | 37 | extern void irq0(); 38 | extern void irq1(); 39 | extern void irq2(); 40 | extern void irq3(); 41 | extern void irq4(); 42 | extern void irq5(); 43 | extern void irq6(); 44 | extern void irq7(); 45 | extern void irq8(); 46 | extern void irq9(); 47 | extern void irq10(); 48 | extern void irq11(); 49 | extern void irq12(); 50 | extern void irq13(); 51 | extern void irq14(); 52 | extern void irq15(); 53 | 54 | #define IRQ0 32 55 | #define IRQ1 33 56 | #define IRQ2 34 57 | #define IRQ3 35 58 | #define IRQ4 36 59 | #define IRQ5 37 60 | #define IRQ6 38 61 | #define IRQ7 39 62 | #define IRQ8 40 63 | #define IRQ9 41 64 | #define IRQ10 42 65 | #define IRQ11 43 66 | #define IRQ12 44 67 | #define IRQ13 45 68 | #define IRQ14 46 69 | #define IRQ15 47 70 | 71 | struct regs{ 72 | unsigned int ds; 73 | unsigned int edi, esi, ebp, esp, ebx, ecx, eax; 74 | unsigned int int_no, err_code; 75 | unsigned int eip, cs, eflags, useresp, ss; 76 | }; 77 | 78 | typedef void (*isr_t)(struct regs); 79 | 80 | void irq_install(); 81 | void isr_handler(struct regs r); 82 | void irq_handler(struct regs r); 83 | void irq_install_handlers(unsigned char n, isr_t handler); 84 | 85 | #endif 86 | -------------------------------------------------------------------------------- /cpu/kb.c: -------------------------------------------------------------------------------- 1 | #include "kb.h" 2 | #include "irq.h" 3 | 4 | void keyboard_handler(struct regs r){ 5 | 6 | } 7 | 8 | void keyboard_install(){ 9 | irq_install_handlers(IRQ1, keyboard_handler); 10 | } 11 | -------------------------------------------------------------------------------- /cpu/kb.h: -------------------------------------------------------------------------------- 1 | #ifndef __KB_H__ 2 | #define __KB_H__ 3 | 4 | void keyboard_handler(); 5 | void keyboard_install(); 6 | 7 | #endif 8 | -------------------------------------------------------------------------------- /cpu/timer.c: -------------------------------------------------------------------------------- 1 | #include "timer.h" 2 | #include "../include/print.h" 3 | #include "../include/ports.h" 4 | #include "../cpu/irq.h" 5 | 6 | unsigned int tick=0; 7 | 8 | void timer_handler(struct regs r){ 9 | tick++; 10 | unsigned int s=0; 11 | if(tick%18==0){ 12 | print_num(s++); 13 | print(" has passed\n"); 14 | } 15 | } 16 | 17 | void timer_install(){ 18 | irq_install_handlers(IRQ0, timer_handler); 19 | } 20 | 21 | void init_timer(unsigned int freq){ 22 | irq_install(); 23 | unsigned int divisor=1193180/freq; 24 | unsigned char low=(unsigned char)(divisor & 0XFF); 25 | unsigned char high=(unsigned char)((divisor >> 8) & 0XFF); 26 | 27 | outb(0X43, 0X36); 28 | outb(0X40, low); 29 | outb(0X40, high); 30 | } 31 | -------------------------------------------------------------------------------- /cpu/timer.h: -------------------------------------------------------------------------------- 1 | #ifndef __TIMER_H__ 2 | #define __TIMER_H__ 3 | 4 | void init_timer(unsigned int freq); 5 | void timer_install(); 6 | 7 | #endif 8 | -------------------------------------------------------------------------------- /include/README.md: -------------------------------------------------------------------------------- 1 | # Libraries 2 | -------------------------------------------------------------------------------- /include/about.h: -------------------------------------------------------------------------------- 1 | #ifndef __ABOUT_H__ 2 | #define __ABOUT_H__ 3 | 4 | #define OS_NAME "MYOS" 5 | #define VERSION "0.1" 6 | #define DEVELOPER "Nikhil Kumar Tomar" 7 | #define OS_DESC "Maya is a simple command-line based OS , developed as hooby project during January 2016." 8 | void os_about(){ 9 | print("\nOS NAME: "); 10 | print(OS_NAME); 11 | print("\nVersion: "); 12 | print(VERSION); 13 | print("\nDeveloper: "); 14 | print(DEVELOPER); 15 | print("\n"); 16 | } 17 | 18 | void os_logo(){ 19 | 20 | } 21 | #endif 22 | -------------------------------------------------------------------------------- /include/input.h: -------------------------------------------------------------------------------- 1 | #ifndef KB_H 2 | #define KB_H 3 | #include "print.h" 4 | #include "ports.h" 5 | #include "string.h" 6 | 7 | char* readStr() 8 | { 9 | char buff; 10 | char* buffstr=""; 11 | unsigned char i = 0; 12 | unsigned char reading = 1; 13 | unsigned char shift=0; 14 | while(reading) 15 | { 16 | if(inb(0x64) & 0x1) 17 | { 18 | unsigned char scancode=inb(0X60); 19 | if(scancode==0x2a || scancode==0x36){ 20 | shift=1; 21 | }else if(scancode==0xaa || scancode==0xb6){ 22 | shift=0; 23 | } 24 | if(shift==1){ 25 | 26 | switch(scancode) 27 | { 28 | /*case 1: 29 | print("(char)27); Escape button 30 | buffstr[i] = (char)27; 31 | i++; 32 | break;*/ 33 | case 2: 34 | print("!"); 35 | buffstr[i] = '!'; 36 | i++; 37 | break; 38 | case 3: 39 | print("@"); 40 | buffstr[i] = '@'; 41 | i++; 42 | break; 43 | case 4: 44 | print("#"); 45 | buffstr[i] = '#'; 46 | i++; 47 | break; 48 | case 5: 49 | print("$"); 50 | buffstr[i] = '$'; 51 | i++; 52 | break; 53 | case 6: 54 | print("%"); 55 | buffstr[i] = '%'; 56 | i++; 57 | break; 58 | case 7: 59 | print("^"); 60 | buffstr[i] = '^'; 61 | i++; 62 | break; 63 | case 8: 64 | print("&"); 65 | buffstr[i] = '&'; 66 | i++; 67 | break; 68 | case 9: 69 | print("*"); 70 | buffstr[i] = '*'; 71 | i++; 72 | break; 73 | case 10: 74 | print("("); 75 | buffstr[i] = '('; 76 | i++; 77 | break; 78 | case 11: 79 | print(")"); 80 | buffstr[i] = ')'; 81 | i++; 82 | break; 83 | case 12: 84 | print("-"); 85 | buffstr[i] = '_'; 86 | i++; 87 | break; 88 | case 13: 89 | print("+"); 90 | buffstr[i] = '+'; 91 | i++; 92 | break; 93 | case 14: 94 | i--; 95 | buffstr[i] = '\n'; 96 | back_cursor(strlen(buffstr)); 97 | break; 98 | /* case 15: 99 | print("\t"); Tab button 100 | buffstr[i] = '\t'; 101 | i++; 102 | break;*/ 103 | case 16: 104 | print("Q"); 105 | buffstr[i] = 'Q'; 106 | i++; 107 | break; 108 | case 17: 109 | print("W"); 110 | buffstr[i] = 'W'; 111 | i++; 112 | break; 113 | case 18: 114 | print("E"); 115 | buffstr[i] = 'E'; 116 | i++; 117 | break; 118 | case 19: 119 | print("R"); 120 | buffstr[i] = 'R'; 121 | i++; 122 | break; 123 | case 20: 124 | print("T"); 125 | buffstr[i] = 'T'; 126 | i++; 127 | break; 128 | case 21: 129 | print("Y"); 130 | buffstr[i] = 'Y'; 131 | i++; 132 | break; 133 | case 22: 134 | print("U"); 135 | buffstr[i] = 'U'; 136 | i++; 137 | break; 138 | case 23: 139 | print("I"); 140 | buffstr[i] = 'I'; 141 | i++; 142 | break; 143 | case 24: 144 | print("O"); 145 | buffstr[i] = 'O'; 146 | i++; 147 | break; 148 | case 25: 149 | print("P"); 150 | buffstr[i] = 'P'; 151 | i++; 152 | break; 153 | case 26: 154 | print("{"); 155 | buffstr[i] = '}'; 156 | i++; 157 | break; 158 | case 27: 159 | print("}"); 160 | buffstr[i] = '}'; 161 | i++; 162 | break; 163 | case 28: 164 | // print("\n"); 165 | buffstr[i] = '\n'; 166 | //i++; 167 | reading = 0; 168 | break; 169 | /* case 29: 170 | print("q"); Left Control 171 | buffstr[i] = 'q'; 172 | i++; 173 | break;*/ 174 | case 30: 175 | print("A"); 176 | buffstr[i] = 'A'; 177 | i++; 178 | break; 179 | case 31: 180 | print("S"); 181 | buffstr[i] = 'S'; 182 | i++; 183 | break; 184 | case 32: 185 | print("D"); 186 | buffstr[i] = 'D'; 187 | i++; 188 | break; 189 | case 33: 190 | print("F"); 191 | buffstr[i] = 'F'; 192 | i++; 193 | break; 194 | case 34: 195 | print("G"); 196 | buffstr[i] = 'G'; 197 | i++; 198 | break; 199 | case 35: 200 | print("H"); 201 | buffstr[i] = 'H'; 202 | i++; 203 | break; 204 | case 36: 205 | print("J"); 206 | buffstr[i] = 'J'; 207 | i++; 208 | break; 209 | case 37: 210 | print("K"); 211 | buffstr[i] = 'K'; 212 | i++; 213 | break; 214 | case 38: 215 | print("L"); 216 | buffstr[i] = 'L'; 217 | i++; 218 | break; 219 | case 39: 220 | print(":"); 221 | buffstr[i] = ':'; 222 | i++; 223 | break; 224 | case 40: 225 | print((char*)'"'); // Double quote (") 226 | buffstr[i] = (char)44; 227 | i++; 228 | break; 229 | case 41: 230 | print((char*)"~"); // (~) 231 | buffstr[i] = (char)44; 232 | i++; 233 | break; 234 | case 42: // Left shift 235 | //shift=1; 236 | i++; 237 | break; 238 | case 43: 239 | print("|"); 240 | buffstr[i] = '|'; 241 | i++; 242 | break; 243 | case 44: 244 | print("Z"); 245 | buffstr[i] = 'Z'; 246 | i++; 247 | break; 248 | case 45: 249 | print("X"); 250 | buffstr[i] = 'X'; 251 | i++; 252 | break; 253 | case 46: 254 | print("C"); 255 | buffstr[i] = 'C'; 256 | i++; 257 | break; 258 | case 47: 259 | print("V"); 260 | buffstr[i] = 'V'; 261 | i++; 262 | break; 263 | case 48: 264 | print("B"); 265 | buffstr[i] = 'B'; 266 | i++; 267 | break; 268 | case 49: 269 | print("N"); 270 | buffstr[i] = 'N'; 271 | i++; 272 | break; 273 | case 50: 274 | print("M"); 275 | buffstr[i] = 'M'; 276 | i++; 277 | break; 278 | case 51: 279 | print("<"); 280 | buffstr[i] = '<'; 281 | i++; 282 | break; 283 | case 52: 284 | print(">"); 285 | buffstr[i] = '>'; 286 | i++; 287 | break; 288 | case 53: 289 | print("?"); 290 | buffstr[i] = '?'; 291 | i++; 292 | break; 293 | 294 | case 54: 295 | //shift=1; 296 | i++; 297 | break; 298 | case 55: 299 | print("/"); 300 | buffstr[i] = '/'; 301 | i++; 302 | break; 303 | /*case 56: 304 | print(" "); Right alt 305 | buffstr[i] = ' '; 306 | i++; 307 | break;*/ 308 | case 57: 309 | print(" "); 310 | buffstr[i] = ' '; 311 | i++; 312 | break; 313 | } 314 | 315 | 316 | }else if(shift==0){ 317 | 318 | switch(scancode) 319 | { 320 | /*case 1: 321 | print("(char)27); Escape button 322 | buffstr[i] = (char)27; 323 | i++; 324 | break;*/ 325 | case 2: 326 | print("1"); 327 | buffstr[i] = '1'; 328 | i++; 329 | break; 330 | case 3: 331 | print("2"); 332 | buffstr[i] = '2'; 333 | i++; 334 | break; 335 | case 4: 336 | print("3"); 337 | buffstr[i] = '3'; 338 | i++; 339 | break; 340 | case 5: 341 | print("4"); 342 | buffstr[i] = '4'; 343 | i++; 344 | break; 345 | case 6: 346 | print("5"); 347 | buffstr[i] = '5'; 348 | i++; 349 | break; 350 | case 7: 351 | print("6"); 352 | buffstr[i] = '6'; 353 | i++; 354 | break; 355 | case 8: 356 | print("7"); 357 | buffstr[i] = '7'; 358 | i++; 359 | break; 360 | case 9: 361 | print("8"); 362 | buffstr[i] = '8'; 363 | i++; 364 | break; 365 | case 10: 366 | print("9"); 367 | buffstr[i] = '9'; 368 | i++; 369 | break; 370 | case 11: 371 | print("0"); 372 | buffstr[i] = '0'; 373 | i++; 374 | break; 375 | case 12: 376 | print("-"); 377 | buffstr[i] = '-'; 378 | i++; 379 | break; 380 | case 13: 381 | print("="); 382 | buffstr[i] = '='; 383 | i++; 384 | break; 385 | case 14: 386 | i--; 387 | buffstr[i] = '\n'; 388 | back_cursor(strlen(buffstr)); 389 | break; 390 | /* 391 | case 15: 392 | print("\t"); //Tab button 393 | buffstr[i] = '\t'; 394 | i++; 395 | break; 396 | */ 397 | case 16: 398 | print("q"); 399 | buffstr[i] = 'q'; 400 | i++; 401 | break; 402 | case 17: 403 | print("w"); 404 | buffstr[i] = 'w'; 405 | i++; 406 | break; 407 | case 18: 408 | print("e"); 409 | buffstr[i] = 'e'; 410 | i++; 411 | break; 412 | case 19: 413 | print("r"); 414 | buffstr[i] = 'r'; 415 | i++; 416 | break; 417 | case 20: 418 | print("t"); 419 | buffstr[i] = 't'; 420 | i++; 421 | break; 422 | case 21: 423 | print("y"); 424 | buffstr[i] = 'y'; 425 | i++; 426 | break; 427 | case 22: 428 | print("u"); 429 | buffstr[i] = 'u'; 430 | i++; 431 | break; 432 | case 23: 433 | print("i"); 434 | buffstr[i] = 'i'; 435 | i++; 436 | break; 437 | case 24: 438 | print("o"); 439 | buffstr[i] = 'o'; 440 | i++; 441 | break; 442 | case 25: 443 | print("p"); 444 | buffstr[i] = 'p'; 445 | i++; 446 | break; 447 | case 26: 448 | print("["); 449 | buffstr[i] = '['; 450 | i++; 451 | break; 452 | case 27: 453 | print("]"); 454 | buffstr[i] = ']'; 455 | i++; 456 | break; 457 | case 28: 458 | // print("\n"); 459 | buffstr[i] = '\n'; 460 | //i++; 461 | reading = 0; 462 | break; 463 | /* case 29: 464 | print("q"); Left Control 465 | buffstr[i] = 'q'; 466 | i++; 467 | break;*/ 468 | case 30: 469 | print("a"); 470 | buffstr[i] = 'a'; 471 | i++; 472 | break; 473 | case 31: 474 | print("s"); 475 | buffstr[i] = 's'; 476 | i++; 477 | break; 478 | case 32: 479 | print("d"); 480 | buffstr[i] = 'd'; 481 | i++; 482 | break; 483 | case 33: 484 | print("f"); 485 | buffstr[i] = 'f'; 486 | i++; 487 | break; 488 | case 34: 489 | print("g"); 490 | buffstr[i] = 'g'; 491 | i++; 492 | break; 493 | case 35: 494 | print("h"); 495 | buffstr[i] = 'h'; 496 | i++; 497 | break; 498 | case 36: 499 | print("j"); 500 | buffstr[i] = 'j'; 501 | i++; 502 | break; 503 | case 37: 504 | print("k"); 505 | buffstr[i] = 'k'; 506 | i++; 507 | break; 508 | case 38: 509 | print("l"); 510 | buffstr[i] = 'l'; 511 | i++; 512 | break; 513 | case 39: 514 | print(";"); 515 | buffstr[i] = ';'; 516 | i++; 517 | break; 518 | case 40: 519 | print((char*)44); // Single quote (") 520 | buffstr[i] = (char)44; 521 | i++; 522 | break; 523 | case 41: 524 | print((char*)44); 525 | buffstr[i] = (char)44; 526 | i++; 527 | break; 528 | case 42: 529 | //shift=1; 530 | i++; 531 | break; 532 | case 43: 533 | print("\\"); 534 | buffstr[i] = '\\'; 535 | i++; 536 | break; 537 | case 44: 538 | print("z"); 539 | buffstr[i] = 'z'; 540 | i++; 541 | break; 542 | case 45: 543 | print("x"); 544 | buffstr[i] = 'x'; 545 | i++; 546 | break; 547 | case 46: 548 | print("c"); 549 | buffstr[i] = 'c'; 550 | i++; 551 | break; 552 | case 47: 553 | print("v"); 554 | buffstr[i] = 'v'; 555 | i++; 556 | break; 557 | case 48: 558 | print("b"); 559 | buffstr[i] = 'b'; 560 | i++; 561 | break; 562 | case 49: 563 | print("n"); 564 | buffstr[i] = 'n'; 565 | i++; 566 | break; 567 | case 50: 568 | print("m"); 569 | buffstr[i] = 'm'; 570 | i++; 571 | break; 572 | case 51: 573 | print(","); 574 | buffstr[i] = ','; 575 | i++; 576 | break; 577 | case 52: 578 | print("."); 579 | buffstr[i] = '.'; 580 | i++; 581 | break; 582 | case 53: 583 | print("/"); 584 | buffstr[i] = '/'; 585 | i++; 586 | break; 587 | case 54: 588 | //shift=1; 589 | i++; 590 | break; 591 | case 55: 592 | print("/"); 593 | buffstr[i] = '/'; 594 | i++; 595 | break; 596 | /*case 56: 597 | print(" "); Right shift 598 | buffstr[i] = ' '; 599 | i++; 600 | break;*/ 601 | case 57: 602 | print(" "); 603 | buffstr[i] = ' '; 604 | i++; 605 | break; 606 | } 607 | 608 | } 609 | 610 | } 611 | } 612 | buffstr[i] = 0; 613 | return buffstr; 614 | } 615 | #endif 616 | -------------------------------------------------------------------------------- /include/ports.c: -------------------------------------------------------------------------------- 1 | 2 | void outb(unsigned short port, unsigned char data){ 3 | asm volatile("outb %0, %1": :"a"(data), "dN"(port)); 4 | } 5 | 6 | unsigned char inb(unsigned short port){ 7 | unsigned short ret; 8 | asm volatile("inw %1, %0" : "=a"(ret) : "dN"(port)); 9 | return ret; 10 | } 11 | -------------------------------------------------------------------------------- /include/ports.h: -------------------------------------------------------------------------------- 1 | #ifndef __PORTS_H__ 2 | #define __PORTS_H__ 3 | 4 | void outb(unsigned short port, unsigned char data); 5 | unsigned char inb(unsigned short port); 6 | 7 | #endif 8 | -------------------------------------------------------------------------------- /include/print.c: -------------------------------------------------------------------------------- 1 | #include "print.h" 2 | #include "ports.h" 3 | #include "string.h" 4 | 5 | char default_color=0xf0; 6 | 7 | char* vidmem=(char*)0xb8000; 8 | static unsigned int curx=0, cury=0; 9 | 10 | void clearLine(int from, int to, char color) 11 | { 12 | int i=0; 13 | for(i=from*COLS*2;i> 8); 34 | outb(0x3D4, 15); 35 | outb(0x3D5, loc); 36 | } 37 | 38 | void scroll(int line){ 39 | unsigned short i = 0; 40 | clearLine(0,line-1, default_color); 41 | for (i;i 0) 79 | { 80 | curx--; 81 | vidmem[(curx * COLS + curx)*2]=color; 82 | } 83 | break; 84 | case (0x09): 85 | curx = (curx + 8) & ~(8 - 1); 86 | break; 87 | case ('\r'): 88 | curx= 0; 89 | break; 90 | case ('\n'): 91 | curx = 0; 92 | cury++; 93 | break; 94 | default: 95 | vidmem [((cury * COLS + curx))*2] = c; 96 | vidmem [((cury * COLS + curx))*2+1] = color; 97 | curx++; 98 | break; 99 | 100 | } 101 | if(curx >= COLS) 102 | { 103 | curx = 0; 104 | cury++; 105 | } 106 | if(cury>=ROWS-2){ 107 | scroll(1); 108 | } 109 | move_cursor(); 110 | } 111 | 112 | void print (char* ch) 113 | { 114 | int i = 0; 115 | int length = strlen(ch); 116 | for(i=0;i0){ 142 | //here 8 is the length of the shell line e.g "shell:# " (1 space) 143 | if(curx>8){ 144 | curx--; 145 | vidmem [((cury * COLS + curx))*2] = 0x0; 146 | vidmem [((cury * COLS + curx))*2+1] = default_color; 147 | move_cursor(); 148 | } 149 | } 150 | } 151 | -------------------------------------------------------------------------------- /include/print.h: -------------------------------------------------------------------------------- 1 | #ifndef __PRINT_H__ 2 | #define __PRINT_H__ 3 | 4 | #define ROWS 25 5 | #define COLS 80 6 | 7 | void clearLine(int from, int to, char color); 8 | void clear(char color); 9 | void printch(char c, char color); 10 | void print (char* ch); 11 | void print_color (char* ch, char color); 12 | void print_num(int i); 13 | #endif 14 | -------------------------------------------------------------------------------- /include/string.c: -------------------------------------------------------------------------------- 1 | void reverse(char s[]){ 2 | int c,i,j; 3 | for(i=0, j=strlen(s)-1;i0); 17 | if(sign <0) str[i++]='-'; 18 | str[i]='\0'; 19 | reverse(str); 20 | } 21 | 22 | int strlen(char s[]){ 23 | int i=0; 24 | while(s[i]!='\0') i++; 25 | return i++; 26 | } 27 | 28 | int strcmp(char str1[], char str2[]){ 29 | int i=0,flag=0; 30 | 31 | while(str1[i]!='\0' && str2[i]!='\0'){ 32 | if(str1[i]!=str2[i]){ 33 | flag=1; 34 | break; 35 | } 36 | i++; 37 | } 38 | 39 | if (flag==0 && str1[i]=='\0' && str2[i]=='\0') 40 | return 1; 41 | else 42 | return 0; 43 | } 44 | /* 45 | 46 | int strcmp(char s1[], char s2[]) { 47 | int i; 48 | for (i = 0; s1[i] == s2[i]; i++) { 49 | if (s1[i] == '\0') return 0; 50 | } 51 | return s1[i] - s2[i]; 52 | } 53 | */ 54 | void concat(char* a, char* b, char* c){ 55 | int len = strlen(a)+strlen(b); 56 | int i = 0; 57 | while(i < strlen(a)){ 58 | c[i] = a[i]; 59 | i++; 60 | } 61 | i = 0; 62 | while(i < strlen(b)){ 63 | c[i+strlen(a)] = b[i]; 64 | i++; 65 | } 66 | c[len] = '\0'; 67 | } 68 | 69 | void concatc(char* a, char b, char* c){ 70 | int len = strlen(a)+1; 71 | int i = 0; 72 | while(i < strlen(a)){ 73 | c[i] = a[i]; 74 | i++; 75 | } 76 | c[i] = b; 77 | c[len] = '\0'; 78 | } 79 | 80 | void remchar(char* a, char* b){ 81 | int i = 0; 82 | while(i < strlen(a)-1){ 83 | b[i] = a[i]; 84 | i++; 85 | } 86 | b[i] = '\0'; 87 | } 88 | 89 | int toHex(char c){ 90 | if(c == '0'){ 91 | return 0x0; 92 | }if(c == '1'){ 93 | return 0x1; 94 | }if(c == '2'){ 95 | return 0x2; 96 | }if(c == '3'){ 97 | return 0x3; 98 | }if(c == '4'){ 99 | return 0x4; 100 | }if(c == '5'){ 101 | return 0x5; 102 | }if(c == '6'){ 103 | return 0x6; 104 | }if(c == '7'){ 105 | return 0x7; 106 | }if(c == '8'){ 107 | return 0x8; 108 | }if(c == '9'){ 109 | return 0x9; 110 | }if(c == 'a' || c == 'A'){ 111 | return 0xa; 112 | }if(c == 'b' || c == 'B'){ 113 | return 0xb; 114 | }if(c == 'c' || c == 'C'){ 115 | return 0xc; 116 | }if(c == 'd' || c == 'D'){ 117 | return 0xd; 118 | }if(c == 'e' || c == 'E'){ 119 | return 0xe; 120 | }if(c == 'f' || c == 'F'){ 121 | return 0xf; 122 | } 123 | return -1; 124 | } 125 | 126 | int strncmp(char* a, char* b, int l){ 127 | int c = 0; 128 | 129 | while (a[c] == b[c] && c < l) { 130 | c++; 131 | } 132 | 133 | if (c == l) 134 | return 1; 135 | else 136 | return 0; 137 | } 138 | 139 | int startswith(char* a, char* b){ 140 | return strncmp(a,b,strlen(b)); 141 | } 142 | 143 | void strcpy(char a[], char b[]){ 144 | int i; 145 | for(i = 0; i < strlen(a); i++){ 146 | b[i] = a[i]; 147 | } 148 | } 149 | 150 | char tolower(char a){ 151 | if(a >= 'A' && a <= 'Z') 152 | return a+32; 153 | return a; 154 | } 155 | 156 | void strtolower(char a[], char b[]){ 157 | int i; 158 | for(i = 0; i < strlen(a); i++){ 159 | b[i] = tolower(a[i]); 160 | } 161 | } 162 | 163 | void subchar(char a[], char b[], int index){ 164 | int i = index; 165 | while(i < strlen(a)){ 166 | b[i-index] = a[i]; 167 | i++; 168 | } 169 | b[i-index] = '\0'; 170 | } 171 | 172 | void append(char s[], char n){ 173 | int len=strlen(s); 174 | s[len]=n; 175 | s[len+1]='\0'; 176 | } 177 | 178 | void backspace(char s[]){ 179 | int len=strlen(s); 180 | s[len-1]='\0'; 181 | } 182 | 183 | void memcpy(char* src, char* dst, int nbytes){ 184 | int i; 185 | for(i=0;i