gcc
: C program์ ์ปดํ์ผํ๋ค.
gcc -o ex1 ex1.c
-o
์ต์
์ผ๋ก executable file name์ ์ง์ ํ ์ ์๋ค../ex1
๋ช
๋ น์ด ์ฌ์ฉg++
: C++ program ์ ์ปดํ์ผํ๋ค.
g++ -o ex1 ex1.cpp
kill
: process์๊ฒ ์ ํธ๋ฅผ ๋ณด๋ธ๋ค.
kill 1234
pid
๊ฐ โ1234โ์ธ process๋ฅผ killํ๋ค.^c
: ํ์ฌ ์คํ๋๊ณ ์๋ process๋ฅผ โkillโํ๋ค.
^
์ด๋ ํค๋ณด๋์์ ์ปจํธ๋กค ํค(control)๋ฅผ ์๋ฏธํ๋ค.^c
๋ Ctrl ํค๋ cํค๋ฅผ ๋์์ ๋๋ฅด๋ฉด ๋๋ค. (๋ณต์ฌ ๋จ์ถ์ด์ฒ๋ผ)file *
will show the information for all files in the current directory. Combine file *
and grep
using the pipe symbol(|
) to display file information only for text files.$ file * | grep text
stdio.h
, and the location of utility programs (or Linux commands) such as ls
. Use whereis
command.cd
without arguments will move you to your login directory). Make ex1.c using vi. Compile with gcc
and run.vi ex1.c
#include <stdio.h>
void main(){
printf(`hello\n`);
}
$ gcc -o ex1 ex1.c
$ ./ex1
hello
To compile with g++
, change void main()
=> int main()
#include <stdio.h>
int main(){
printf(`hello\n);
}
$ g++ -o ex1 ex1.c
$ ./ex1
hello
cat
and xxd
. With xxd
, you can see the ascii code for each character in ex1.c. Find the ascii codes for the first line of the program: #include <stdio.h>
.2369 6e63 6c75 6465 203c 7374 6469 6f2e 683e
cat
to see ex1. Why?If use xxd
command
If use cat
command
cat
to see ex1. Because ex1 was written by a Machine code. 55 -- push rbp
48 89 e5 -- mov rbp, rsp
bf f0 05 40 00 -- mov edi, 0x40005f0
.........
Find these machine instructions in ex1 with xxd
. Use /pattern
command in vi to search for a string.
$ xxd ex1 > x
$ vi x
>
symbol.$ ./ex1 > f1
hello
in all files (use -nr option).ps -ef
.ps -ef
shows all the processes in the system. How do you know which ones are yours? Use tty
for this purpose. Note that when a user logs in, the system allocates a terminal, and you can find the terminal number with tty
command. What is your terminal number?My terminal number is pts/13
.
hello
.printf("hello");
fflush(stdout); // to make it print hello immediately
for(;;);
ps
to check its status. &
puts the process in the background so that you can type next command.$ ./ex1 &
$ ps
kill
command.
objdump -D -M intel ex1
to dump the assembly code of ex1.c. Find <main>.
00000000004005bc <main>:
4005bc: 55 push rbp
4005bd: 48 89 e5 mov rbp,rsp
4005c0: bf 90 06 40 00 mov edi,0x400690
4005c5: b8 00 00 00 00 mov eax,0x0
4005ca: e8 c1 fe ff ff call 400490 <printf@plt>
4005cf: 48 8b 05 6a 0a 20 00 mov rax,QWORD PTR [rip+0x200a6a] # 601040 <__TMC_END__>
4005d6: 48 89 c7 mov rdi,rax
4005d9: e8 e2 fe ff ff call 4004c0 <fflush@plt>
4005de: eb fe jmp 4005de <main+0x22>
#include <stdio.h>
#include <string.h>
int main(){
char buf[20];
printf("enter a sentence\n");
gets(buf);
printf("I got %s from you. length:%d\n", buf, strlen(buf));
printf("enter the same sentence again\n");
fgets(buf, 20, stdin);
printf("I got %s from you. length:%d\n", buf, strlen(buf));
}
It causes wanings. (warning: โgetsโ is deprecated (declared at /usr/include/stdio.h:640) [-Wdeprecated-declarations]
)
gets
is deprecated because itโs dangerous, it may cause buffer overflow.
gets()
keeps reading input until newline character or end-of-file is reached. It stores that into a string variable and it is possible that we get buffer overflow error when the buffer for gets()
overflows.
fgets()
is a safer version of gets()
where you can provide limitation on input size. You can also decide to take input from which stream(e.g. File or standard input).
man gets
or man fgets
to find out the usage of them.Enter a sentence
aa bcd e e ff aa bcd bcd hijk lmn al bcd
You entered aa bcd e e ff aa bcd bcd hijk lmn al bcd
xxd
. Interpret them.#include <stdio.h>
xxd
. Interpret them. An executable file in Linux follows ELF (Executable and Linkable Format) format as below.-bash-4.2$ xxd -l 20 ex1
0000000: 7f45 4c46 0201 0100 0000 0000 0000 0000 .ELF............
0000010: 0200 3e00 ..>.
ELF format= ELF header + Program header table + Section 1 + Section 2 + ... + Section n + Section header table
ELF header =
e_ident(16)+e_type(2)+e_machine(2)+e_version(4)+e_entry(4)+e_phoff(4)+e_shoff(4)+
e_flags(4)+e_ehsize(2)+e_phentsize(2)+e_phnum(2)+e_shentsize(2)+e_shnum(2)+
e_shstrndx(2)
e_ident=7f E L F + EI_CLASS(1) + EI_DATA(1) + EI_VERSION(1) + EI_OSABI(1) + EI_ABIVERSION(1) + EI_PAD(7)
EI_CLASS = 1 if 32bit application or 2 if 64bit application
EI_DATA = 1 if little endian or 2 if big endian
EI_VERSION = 1
EI_OSABI = 0 for System V, 1 for HP-UX, 2 for NetBSD, 3 for Linux, 4 for GNU Hurd, ...
EI_ABIVERSION = depends on ABI version
EI_PAD = 9 zero's
e_type= 1 for relocatable file, 2 for executable file, 3 for shared object file
e_machine = 3 for x386, 0x32 for IA-64, 0x3e for amd64, ...
e_version = 1
e_entry = program starting address
.................
(* Refer to https://en.wikipedia.org/wiki/Executable_and_Linkable_Format for the rest of ELF file format)
7f 45 4c 46
is a 4-byte magic number to identify that it is an ELF file and contains a value of 7f 45(E) 4c(L) 46(F).02
indicates the class or capacity of the file.
01
indicates data encoding method information.
01
is the ELF header version number, and EV_CURRENT = 1 is currently used.00 00 00 00 00 00 00 00 00
currently unused, should be filled with zeros.02 00
identifies object file type.
3e 00
specifies target instruction set architecture.