Вы находитесь на странице: 1из 430

-

-
2012

681.3.06
32.973.26-018.2
60

. .
60

Linux-. .: -, 2012. 432 .


( )
ISBN 978-5-9775-0747-9
Linux: bash tcsh Tk, glib, GTK+ dialog,
C/C++ Linux:
gcc, / Linux, , /,
. TCL.
, gdb
gprof.

681.3.06
32.973.26-018.2

:

.
.

30.09.11.
70 1001/16. . . . . 34,83.
1200 .
"-", 190005, -, ., 29.
-
77.99.60.953..005770.05.09 26.05.2009 .
.

" ""
199034, -, 9 , 12

ISBN 978-5-9775-0747-9

. ., 2011
, "-", 2011

.......................................................................................................................... 11
I.
...................................................................................... 13
1. ...................................................................... 14
1.1. /etc/shells ....................................................................................................................... 14
1.2. sh ............................................................................................................................ 15
1.3. csh .......................................................................................................................... 16
1.4. ksh .......................................................................................................................... 16
1.5. bash ........................................................................................................................ 17
1.6. zsh ........................................................................................................................... 17
1.7. tcsh ......................................................................................................................... 18
1.8. ash .......................................................................................................................... 19
1.9. ..................................................................................................................... 19

2. bash ................................................................ 20
2.1. bash ....................................................................................................................... 20
2.2. bash................................................................................. 22
2.3. , ! ........................................................................................................................... 23
2.4. ...................................................... 23
2.5. ........................................................................................... 25
2.6. bash ...................................................................................................................... 25
2.7. ...................................................................................................................................... 26
2.8. ............................................................................................................. 27
2.9. .................................................................................................................................. 28
2.10. ............................................................................................................. 28
2.10.1. .............................................................................. 28
2.10.2. ........................................................................................... 29
2.10.3. .......................................................................... 30

3. tcsh ......................................................................... 31
3.1. tcsh ................................................................................................................ 31
3.2. tcsh ............................................................................................ 32

3.3. tcsh ................................................................................................... 33


3.3.1. , .......................................................................... 33
3.3.2. ......................................................................................... 36
3.3.3. tcsh ......................................................................................... 36
3.3.4. ............................................................................................ 38
if ................................................................................................. 38
if..then..else ................................................................................ 39
foreach ......................................................................................................... 40
while ............................................................................................................ 41
switch ........................................................................................................... 41
3.3.5. tcsh .......................................................................................... 42

4. dialog: ................ 45
4.1. ........................................................................ 45
4.2. ............................................................................................... 46
4.3. .......................................................................................................... 47
4.4. ............................................................................................................................. 49
4.5. ....................................................................................................................... 51
4.6. : .......................................... 52
4.7. .......................................................................................................... 54
4.8. ............................................................................................................................... 55
4.9. ............................................................................................................. 56
4.10. ........................................................................................... 57

5. gcc .................................. 60
5.1. .................................................................................................................... 60
5.2. gcc ...................................................................................................................... 61
5.2.1. .............................................................................................. 61
5.2.2. Linux ................................................................... 62
5.2.3. .................................................................................................... 63
5.3. ........................................................................................ 65
5.3.1. .......................................................................... 65
5.3.2. Makefile ..................................................................................................... 66

II. C LINUX....................... 59
6. . ................................... 71
6.1. ............................................................................ 71
6.2. ....................................................................................... 73
6.3. .................................................................................... 75

7. ............................................................................... 78
7.1. ............................................................................... 78
7.2. ? ............................................................................................................ 78
7.3. .......................................................... 80
7.4. ...................................................................................................... 81

8. / Linux ....................................................................................... 83
8.1. /. / ................. 83
8.2. C / ................................................. 85

8.3. / ................................................................................................ 89
8.3.1. / ........................................................... 89
8.3.2. creat() ............................................................................................ 92
8.3.3. : open() read() .................................................... 93
8.3.4. write() ............................................................................................ 95
8.3.5. lseek()............................................................................................. 97

III. .......................................... 99
9. .................................................................... 100
9.1. Linux.......................................................................................... 100
9.1.1. .................................................................................................. 100
9.1.2. ............................................................................. 102
9.1.3. top: ........................ 105
9.1.4. nice renice: ....................................... 107
9.2. system() .................................................................................................................. 107

10. .................................... 109


10.1. ............................................................................................ 109
10.1.1. ................................................................ 109
10.1.2. fork() .................................................................................................. 111
10.1.3. exec ........................................................................................ 113
10.2. wait(): ........................... 117
10.3. ........................................................................................................... 119
10.4. ................................................................................. 120

11. ................................................................. 122


11.1. ............................................................................................................. 122
11.2. pthread_create() .................................................................................................. 123
11.3. ....................................................................... 126
11.4. : pthread_exit()................................................ 128
11.5. : pthread_join() ....................................... 129
11.6. ..................................................................................... 132
11.7. ............................................................................................................ 132

12. ...................................................................... 133


12.1. .................................................................................................. 133
12.2. ................................................................................................................................ 133
12.3. FIFO ...................................................................................... 137
12.4. ........................................................................................................... 140
12.4.1. System V ........................................................... 140
12.4.2. .............................................................. 141
12.4.3. ................................................................................ 143
12.4.4. ........................................................................... 145
12.5. ........................................................................................................................... 149
12.5.1. ............................................................................................. 149
12.5.2. ....................................................................................................... 149
12.5.3. ................................................................................... 150
12.5.4. ..................................................................................... 151
12.5.5. .......................................................................................... 152

12.6. ......................................................................................... 154


12.6.1. ....................................................................................................... 154
12.6.2. .............................. 154
12.6.3. ............................................................................... 156

13. .............................................................................. 158


13.1. ....................................................................................................... 158
13.2. lsmod, insmod, modprobe ................................................................................... 159
13.3. ..................................................................................... 161
13.4. ........................................................................................................... 162
13.5. ........................................................................................................... 165
13.6. ...................................................................................................... 168
13.7. ................................................................................................. 172
13.8. ................................................................................. 172
13.8.1. ..................................................... 172
13.8.2. , .......................................... 173
13.8.3. .................................................................................... 174
13.9. .................................................................................................... 175
13.9.1. ............................................................................................. 175
13.9.2. .......................................................................................... 177
13.9.3. .................................................. 177
13.10. /proc .................................................................................................... 183
13.11. : ...................................................................... 187

IV. LINUX........................................................ 193


14. ................................................................ 194
14.1. Linux ..................................................................................... 194
14.2. Linux ............................................................................ 195
14.2.1. Linux ............................................................................................. 195
14.2.2. ................................................................................................ 196
14.2.3. ....................................................... 197
14.2.4. Linux .................................................................................. 197
14.3. ........................................................................ 198
14.4. ...................................................................................... 201
14.4.1. mount umount........................................................................................ 201
14.4.2. ......................................................................... 202
........................................................................................................... 202
.................................................................................... 204
..................................................................................................................... 204
USB- ............................................................................................... 204
14.4.3. ................................................................ 205
14.4.4. ................................................................... 206
14.4.5. UUID /etc/fstab ...................................................................... 208
14.4.6. mount() ...................................................................................... 210

15. ...................................................................... 213


15.1. ................................................................................... 213
15.2. ................................................................................... 215
15.2.1. ................................................................................ 215

15.2.2. , .............................................................. 215


15.2.3. ......................................................................... 217
15.2.4. ............................................................................... 219

16. ................................................................................ 220


16.1. ....................................................................................... 220
16.2. ...................................................................... 223
16.2.1. : rename() .......................................................................... 223
16.2.2. : unlink() rmdir() .................................................... 223
16.2.3. umask() ...................................................................................... 224
16.2.4. ................................................................................................. 224

17. ...................................... 226


17.1. ....................................................................... 226
17.2. basename() getcwd() ........................................................................................ 229

18. .................................................. 230


18.1. . chmod() ..................................................... 230
18.2. . chown() ....................................................... 233

19. ....................................................................... 234


19.1. .................................................................................. 234
19.2. sysfs................................................................................ 235
19.3. /proc ............................................................................... 235
19.3.1. ........................................................................................ 236
19.3.2. , ................................................. 236
19.3.3. , ................................................................... 237
19.3.4. , ........................................ 238
19.3.5. , ........................... 238
19.3.6. ....................................................................................... 238

V. ................................................. 241
20. TCP/IP .................................................................................... 242
20.1. OSI ......................................................................................................................... 242
20.2. ............................................................................................................ 244
20.3. ................................................................................................... 245

21. : ..................................................... 249


21.1. ................................................................................................................... 249
21.2. .......................................................................................... 250
21.3. ............................................................. 252
21.4. ................................................................................................................ 254
21.5. ................................................................................................... 255

22. : ................................................ 256


22.1. / ............................................................................... 256
22.1.1. - ................................................................................................... 256
22.1.2. - .................................................................................................. 259
22.2. .............................................................................................................. 260

22.3. , ........................................................................................ 263


22.4. ................................................................................................ 264

VI.
TCL/TK ............................................................................................ 265
23. TCL/Tk ................................................................................... 266
23.1. TCL .............................................................................................................. 266
23.2. TCL/Tk ............................................................................................................. 266
23.3. .............................................................................................................. 267

24. TCL .......................................................................................... 270


24.1. TCL ........................................................................................ 270
24.1.1. TCL- ............................................................................................ 270
24.1.2. puts format: ................................... 271
24.1.3. ........................................................................................ 272
24.1.4. ............................................................................................................. 272
24.1.5. ............................................................................................................... 274
24.1.6. .................................................................................. 274
24.1.7. ..................................................................................... 275
24.1.8. if ................................................................................................ 276
24.1.9. while .......................................................................................................... 277
24.1.10. for ............................................................................................................ 277
24.2. ................................................................................................................................. 277
24.2.1. string ......................................................................................................... 277
24.2.2. ...................................................................................................... 279
24.2.3. ......................................................................... 280
24.2.4. ................................................................................................ 282
24.2.5. ................................................................................................ 283
24.3. ................................................................................................................................. 283
24.3.1. list: ................................................................................ 283
24.3.2. concat: .......................................................................... 284
24.3.3. lappend: ...................................... 284
24.3.4. .................................................................................... 284
24.3.5. ....................................................................................... 285
24.3.6. .................................................................... 285
24.3.7. ....................................................................................................... 285
24.3.8. .................................................................................................. 287
24.3.9. ......................................................... 287
24.3.10. foreach .......................................................................................................... 288
24.4. .............................................................................................................................. 289
24.4.1. ................................................................................ 289
24.4.2. array: ...................................................................... 289
24.5. TCL-..................................................................... 290

25. ...................................................................................... 292


25.1. ........................................................................................ 292
25.2. ...................................................................................................................... 293
25.3. .................................................................................................................... 295
25.4. ......................................................................................... 296

26. .................................................................................. 297


26.1. Tk- ....................................................................................................... 297
26.2. Tk- ............................................................. 300

27. ................................. 302


27.1. pack ...................................................................................................................... 302
27.2. button ................................................................................................................... 304
27.3. checkbutton .......................................................................................................... 307
27.4. ................................................................................................ 311
27.5. ................................................................................................................... 313
27.6. .......................................................................................................................... 315
27.7. ............................................................................................. 318
27.8. . bind .................................................................... 319

28. ...................................................................... 321


28.1. grid ................................................................................................. 321
28.1.1. ................................................................................... 321
28.1.2. ........................................................................................ 323
28.1.3. ................................................................................................. 325
28.2. ............................................................................................................................... 326
28.3. .................................................................................................................... 327
28.4. .......................................................................................................................... 328
28.5. ........................................................................... 330

29. ............................................................................. 332


29.1. ............................................................................................................. 332
29.2. ............................................................................................................ 333
29.3. ................................................................................................................. 336
29.4. ............................................................................................................. 336

VII. GTK+ ......................................................................... 337


30. ...................................................................... 338
30.1. GTK+ ............................................................................................................... 338
30.2. GLib ................................................................................................................ 339
30.2.1. ........................................................................................................... 339
30.2.2. GLib .......................................................................................................... 340
30.2.3. ............................................................................ 341
30.2.4. ...................................................................................................................... 342
30.2.5. ........................................................................................ 344

31. GTK+................................................................... 346


31.1. , , ..................................................................... 346
31.2. ............................................................................................ 347
31.3. .................................................................................................... 348
31.4. . ................................................... 351

32. ...................................................................................................... 354


32.1. ......................................................................................................... 354
32.1.1. ................................................................................................. 354
32.1.2. EventBox ..................................................................................................... 356

10

32.2. GTK ......................................................................................................... 360


32.3. ............................................................................................................ 361
32.4. , .................................................................................... 362
32.5. ...................................................................... 370
32.6. CList ....................................................................................................................... 375
32.7. ...................................................................................................... 379
32.8. .......................................................... 381

33. Glade .................................................................. 382


33.1. ...................................................................................... 382
33.2. Glade ................................................................................................................. 383
33.3. Glade ......................................................................................................... 384
33.4. ......................................................................................................... 388
33.5. .................................................................................................... 390
33.6. ............................................................................................... 390

VIII. ......................... 393


34. . ..................... 394
34.1. ................................................................................... 394
34.2. gdb ................................................................................................... 396
34.3. gdb ............................................................................................... 399
34.4. ...................................................................................... 404

35. ....................................................................... 407


35.1. gprof ........................................................... 407
35.2. ....................................................................... 408

.................................................................................................................. 413
. Linux ........................................................................................... 415
1. ......................................................................................... 415
2. ..................................................................................................................... 417
3. .................................................................................................................. 419

.............................................................................................. 423


Linux . ,
. ,
. .
Linux
bash tcsh C/C++
.
, C C++:
C/C++,
.
Linux. ,
, : , Windows, , , Linux " " (, ).
. I bash tcsh.
dialog, .
.
, : ,
bash, , , .
C: ( )
. , init , C?
C,
. ,
(, , ), . , " ".
C
.

12

, , C, init-ng
(Init Next Generation), ? ...
II C Linux.
gcc, make, , / Linux. , Linux.
, Linux , C. , ,
Linux, II.
III Linux:
(IPC), , . .
, , , . ,
.
Linux IV. , . , , Linux, , ,
.
V .
, .
, /.
VI VII . TCL (, Windows ) Tk, TCL.
( VII) GLib GTK+ GUI. Glade, GTK-.
, VIII . gdb gprof.
, .
. , ,
.



1.

2.

bash

3.

tcsh

4.

dialog:

Linux. ? C. ,
. , awk,
,
. C ...


1.1. /etc/shells
.
, 64- , ,
C. 32-
( x86 x86-64),
.
. , .
, .
. , !
( 1000 )
, Linux, , . ,
, ,
C. , C- -
(, , ).
, .
, . . bash tcsh, Linux. FreeBSD,
bash , . , .
bash. bash, ,
, . , bash
, , ,

1.

15

PATH. , bash
.
.
bash sh, csh, ksh, zsh .
, , /etc/shells. . 1.1 /etc/shells Fedora ( ).
1.1. /etc/shells Fedora
/bin/ash
/bin/bash
/bin/csh
/bin/false
/bin/ksh
/bin/sh
/bin/tcsh
/bin/true
/bin/zsh
/usr/bin/csh
/usr/bin/ksh
/usr/bin/bash
/usr/bin/tcsh
/usr/bin/zsh

.
. , . ,
.

1.1 /bin/false /bin/true . "", , . .
(
chsh). , /bin/false ( /bin/true), . ,
, , "" ,
0 ( false) 1 ( true). .

1.2. sh
()
UNIX (, UNIX, Linux 70- ) sh ( shell). Linux ( FreeBSD).

16

I.

sh (Steve Bourne),
Bourne Shell. sh
AT&T ( Bell Labs). sh
POSIX (Portable Operating System Interface for UNIX UNIX). sh
( )
FreeBSD.
sh ,
, tcsh bash.

1.3. csh
csh (C Shell) FreeBSD. csh BSD (Linux 15). (csh), sh.
csh C,
( ). , , , C.
sh, csh : , , csh , ( ) ( exit). sh
, .
( ) csh
.
FreeBSD Linux csh tcsh, /bin/csh /bin/tcsh.

1.4. ksh
UNIX, .
UNIX AT&T, UNIX ( BSD).
, AT&T . csh, AT&T , ksh (Korn
Shell) (David Korn).
ksh csh: ,
, ,
.

1.

17

1986 , UNIX ,
Linux ( ).
, ksh , FreeBSD Linux
ksh, pdksh,
ksh.
ksh ( bash)
, , .

1.5. bash
bash (Bourne Again Shell) (Free Software Foundation, FSF).
sh.
Linux.
bash sh, sh
, /bin/sh
/bin/bash.
bash , ksh.
, ,
, . csh, bash , .
bash , , Linux, bash.

1.6. zsh
zsh,
.
zsh, bash.
.
zsh? -, . bash
/dir/subdir1/subdir2 :
cd /dir/subdir1/subdir2

bash
<Tab>. :
cd /dir/sub [Tab]/subdi [Tab]

18

I.

zsh :
/d/s/s

<Tab> . ,
/etc/sysconfig/network /e/s/n <Tab>.
, cd .
. , files, f1 f2. f* sources last. :
/files/f1/sources/last
/files/f2/sources/last

/files/f1/sources/last.
/files/f2/sources/last :
cd 1 2

zsh . , , :
< /var/log/messages

, $PAGER.
:
cat /var/log/messages | less

zsh ,
. , :
http://opennet.ru/base/dev/zsh_intro.txt.html;
http://citkit.ru/articles/1083/;
http://alexott.net/ru/writings/zsh/index.html;
http://habrahabr.ru/blogs/linux/82537/.

1.7. tcsh
tcsh csh. t TENEX:
TENEX ( DEC PDP-10).
tcsh , ( bash). , tcsh . root , .
tcsh , ,
bash. tcsh, bash tcsh.

1.

19

1.8. ash
ash (Almquist shell) . , UNIX ( ).
ash 24 10 . ash Linux ( ).
ash sh, sh. NetBSD
ash /bin/sh.

1.9.
?
. , .
. ,
, .
, ,
. , zsh, bash.
bash, tcsh zsh. , . bash,
tcsh ( zsh ). .

bash
2.1. bash
bash

( )
Linux. bash , . , bash ,
, , PATH. , bash .
.
/etc/profile bash,
. /etc/profile ,
bash :
~/.bash_profile ;
~/.bashrc ;
~/.bash_logout .

~/.bash_profile , ,
:
source ~/.bashrc

, .bashrc.
.bashrc. ,
( , : "~" ).
, ,
/etc/profile.
.bash_history ( )
, . , .

2. bash

21

.bashrc? , , , .
alias, :
alias
alias
alias
alias

h='fc -l'
ll='ls -laFo'
l='ls -l'
g='egrep -i'

: l ls -l.
.
PS1 . :
@:_

PS1 :
PS1='\u@\h:\w$'

. 2.1 .
2.1.

\a

ASCII- ( 07).

\d

" , , "

\h

\H

\j

\l

\n

\r

\s

\t

24- (:MM:)

\T

12- (::)

\@

12- (AM/PM)

\u

\v

bash ( )

\V

bash ( : , )

\w

( )

I.

22

2.1 ()

\W

( , )

\!

\#

\$

UID 0, #, $

\\

$ ( )

:
PS1='[\u@\h] $(date +%m/%d/%y) \$'

:
[denis@host] 12/06/10 $

, $()
, .
export,
.

2.2. bash
,
, /etc, /home /usr. ,
:
tar -cvjf _.tar.bz2

DVD
DVD.
( ), . , ? , .
, DVD! , , DVD
.
. ,
.
, ,
. ,
- .
, -

2. bash

23

. ,
,
? , , .

2.3. , !
, : ", !" (Hello, world!).
, nano ee ( 2.1).
2.1.
#!/bin/bash
echo ", !"

,
/bin/bash. : # ! ,
, . , , :
#

echo, .
hello :
$ chmod +x hello

:
./hello

:
, !

hello ( ./), /usr/bin (,


PATH):
# cp ./hello /usr/bin

2.4.

.
,
. ,
, .

I.

24

:
=

:
ADDRESS=www.dkws.org.ua
echo $ADDRESS

:
, -

;
=.

:
read ADDRESS

:
ADDRESS='hostname'


read. .
ADDRESS hostname.
Linux . ,
. :
BASH bash;
BASH_VERSION bash;
HOME , ;
HOSTNAME ;
RANDOM 0 32 767;
OSTYPE ;
PWD ;
PS1 ;
UID ID , ;
USER .

export:
#
$ADDRESS=ww.dkws.org.ua
#
# ADDRESS
export $ADDRESS

2. bash

25

2.5.
,
/. :
$0 ;
$n (n );
$# , .

.
case-esac , ( 2.2).
2.2.
# :
# _
#
case "$1" in
start)
# start
echo " "
;;
stop)
# stop
echo " "
;;
*)
#
# , ,
#
echo "Usage: $0 {start|stop }"
exit 1
;;
esac

, ,
2.2 .

2.6. bash
bash . .

26

I.

:
ARRAY[0]=1
ARRAY[1]=2
echo $ARRAY[0]

2.7.
, bash .
for while, bash until
select, .
for :
for in
do

done

, . , :
for n in 1 2 3;
do
echo $n;
done

: .
, :
1
2
3

while :
while
do

done

while , .
, , . . 1, 2 3, while, for:
n=1
while [ $n -lt 4 ]
do
echo "$n "
n=$(( $n+1 ));
done

2. bash

27

2.8.
bash , if case. if :
if _1 then
_1
elif _2 then
_2
...
elif _N then
_N
else
_N+1
fi

if bash if . , ,
. . elif, ,
.
. . :
#
[
#
[

N = 10
N==10 ]
N 10
N!=10 ]

> <,
:
-lt ;
-gt ;
-le ;
-ge ;
-eq ( ==).

:
[ | ]

:
#
[
#
[

N 10
$N -lt 10 ]
N A
$N -lt $A ]

28

I.

-e , ;
-d , ;
-x , .

case ,
:
case in
_1) _1 ;;
...
_N) _N ;;
*) __;;
esac

(_1 ... _N). ,


, . ,
. case 2.2.

2.9.
bash . :
() { ; }

:
list_txt()
{
echo " "
ls *.txt
}

2.10.
2.10.1.
( 2.3). ,
15 . , , ,
. <Ctrl>+<C>.
2.3.
#!/bin/bash
# ,
INT=3

2. bash

29

while [ true ]
do
# 15
tail -n 15 $1
#
sleep $INT
#
echo; echo
done

:
./ _

:
./script /var/log/messages

2.10.2.
: ,
, ( 2.4).
2.4. rename_blanks
#! /bin/bash
#
#
num=0
#
for filename in *
do
# grep
# ,
# 0
echo "$filename" | grep -q " "
if [ $? -eq 0 ]
then
# 0,
#
fname=$filename
n=`echo $fname | sed -e "s/ /_/g"`
mv "$fname" "$n"
let "num += 1"
fi
done

30

I.

echo " : $num"


exit 0

2.10.3.
,
dc ( 2.5). dc,
.
2.5. dec_hex
#!/ bin/bash
B=16
#
# , $1
if [ -z "$1" ]
then
echo ": dec_hex "
exit 1
fi
# ($1),
# dc
echo ""$1" "$B" o p" | dc

tcsh
3.1. tcsh
1, tcsh
TENEX,
DEC PDP-10.
, Ubuntu, tcsh . :
sudo apt-get install tcsh

, csh.
, (Linux, FreeBSD) /bin/csh
/bin/tcsh.
bash, tcsh , tcsh 65 . builtins.
. 3.1 .
tcsh :
;
, ;
;
.

<Left>
<Right> ( ) <Delete>
<Backspase> ( ). , .
, bash, <Tab>,
<Ctrl>+<I> <Ctrl>+<D>.
, .

I.

32

. 3.1. tcsh

<Up>
<Down>. - (
NFS!), history:
$ history
1
13:08
2
13:09
3
13:19

clear
builtins
history

!#, #
, :
!1

, bash. , &, :
$ command &

jobs.
fg (foreground), ( jobs), :
$ fg 1

bg (background).
fg, :
$ bg 1

3.2. tcsh
tcsh /etc/csh.cshrc, /etc/csh.login,
/etc/csh.logout. tcsh
, tcsh .
tcsh , tcsh ( login shell).

3. tcsh

33

~/.cshrc,
~/.login ~/.logout, /etc/csh.cshrc
/etc/csh.login. /etc/skel (
/usr/share/skel/ ).

tcsh . , .
~/.history, .
( alias), ( setenv), tcsh
( set), . ~/.login,
, ~/.cshrc
.
:
alias hist history 25
alias rm rm -i

hist, 25 .
rm,
rm, -i , .
set, path ( ):
set path = (/bin /usr/bin /usr/local/bin /usr/X11R6/bin)

setenv ( ~/.login), :
setenv EDITOR nano

EDITOR, .

3.3. tcsh
3.3.1. ,
, , set:
set name=denis

name ( denis).
:
echo $name

I.

34

. 3.2. set

set ( ),
, (. 3.2).
unset:
unset name

:
name: Undefined variable.

setenv :
setenv

, . :
setenv

EDITOR

nano

tcsh . :
$ set nums = (one two three four five)
$ echo $nums
one two three four five
$ echo $nums[3]
three
$ echo $nums[1-3]
one two three

3. tcsh

35

, ,
, . 1.
. ,
@, $ .
:
$ @ num = 0
$ echo $num
0
$ @ num = ( 2 + 2 ) * 2
$ echo $num
8
$ @ num += 5
$ echo $num
13
$ @ num++
$ echo $num
14
$ @ num2 = 5
$ @ num = $num2 + 5
$ echo $num
10
$ @ num = 1
echo $nums[$num]
one

, $,
@ $ . @ .
:
@

: =, +=, =, *=, /= %=. , , C. : tcsh


, C,
C-.
:
$ set a = (0 0 0 0 0)
$ @ a[1] = 10
$ @ a[3] = ($ages[1] + 5)
$ echo $a[3]
15

I.

36

3.3.2.
"$<", :
echo -n " : "
set line = "$<"

3.3.3. tcsh
tcsh ,
. 3.1.
3.1. tcsh

argv

(, ). argv[1] , argv[0] .
argv[n] $n,
argv[1] $1. argv[*]

autolist

. . man tcsh

autologout

. 60 ,
. ( )

cdpath

cd, ,
~/.login, :
set cdpath = (/home/denix /home/denix/bin)

cwd

fignore

, tcsh

gid

histfile

, .
~/.history

history

home
HOME

mail

. TC Shell 10

owd

path
PATH

,
tcsh:
set path = ( /usr/bin /bin /usr/local/bin /usr/bin/X11 ~/bin . )

prompt

, PS1
bash. . 3.2. :
set prompt = '! $ '

3. tcsh

37
3.1 ()

prompt2


while foreach

prompt3

savehist

shell

status

tcsh

tcsh

time

. , . - , time, , .
time = 0, .
time (. 3.3),

user

3.2.

%/

%~

, %/,

%! %h !

%m

%M

%n

%t

%p

( )

%d

%D

%W

%y

%Y

%#

(#) (>)

%?

I.

38

3.3.

%U

, (
)

%S

, ( )

%W

%X

%D

, ,

%K

, ( %X+%D),

%M

, ,

%F

%I

%O

, tcsh. , :
$ set aa=abra

,
:
$ echo ${aa}cadabra
abracadabra

3.3.4.
if
if :
if ()

, .
, C. 3.1 ,
, .
3.1. tcsh
#!/bin/tcsh
if ( $#argv == 0 ) echo " "

:
-n _

3. tcsh

39

n . 3.4.
3.4. n
n

(
)

( )

SGID

""

(FIFO)

( )

SUID


, $path

( )

:
if -e $1 echo " "

if..then..else
if..then..else if, else
(), .
:
if () then
,
endif

40

I.

:
if () then
,
else
, ( = false)
endif

, ,
if..then..elif:
if (1) then
( 1 = true)
else if (2) then
( 2 = true)
. . .
else
( true)
endif

( 3.2).
3.2.
#!/bin/tcsh
#
set num = $argv[1]
set flag
#
if ($num < 0) then
@ flag = 1
else if (0 <= $num && $num < 50) then
@ flag = 2
else if (50 <= $num && $num < 1000) then
@ flag = 3
else
@ flag = 4
endif
#
echo "Flag: ${flag}."

foreach
foreach , :
foreach - (-)

end

3. tcsh

41

foreach , :
foreach f ( *.txt )
echo $f
end

. , ls,
foreach.

while
while . , , , :
while ()

end

, n, n ( 3.3).
3.3. while
#!/bin/tcsh
set n = $argv[1]
set i = 1
set fact = 1
#
while ($i <= $n)
@ fact *= $i
@ i++
end
#
echo " $n $fact"

break continue. break , end.


continue end, .

switch
switch , . switch :
switch ()
case 1:
1
breaksw

I.

42
case 2:
2
breaksw
...
default:

breaksw
endsw

:
set string = test
switch (string)
case test:
echo ": test"
breaksw
case text:
echo ": text"
breaksw
default:
echo " "
breaksw
endsw

3.3.5. tcsh
tcsh (, ,
). . 3.5
tcsh.
3.5. tcsh

alias

alloc

bg

builtins

cd chdir

dirs

echo

exec

3. tcsh

43
3.5 ()

exit

tcsh

fg

" ", . .

filetest

.
(, , ),
(. . 3.4)

glob

echo,

hashstat

tcsh

history

jobs

( , )

kill

limit

login

logout

, tcsh

lsF

ls F,

nice

nohup

notify

popd

printenv

pushd

rehash

, .
, /usr/bin. tcsh
,

repeat


( )

sched

, :
$ sched 10:00 echo " 10 !"

set

setenv

source

, .
, .
include

I.

44

3.5 ()

stop

(
)

suspend

time

, .
( )

umask

(. man umask)

unalias

unhash

. . hashstat rehash

unlimit

unset

unsetenv

where

, ,
. which

which

which,
.
, .
, path

dialog:

4.1.

bash tcsh. ,
. ,
- , ,
. , DOS,
, , , /
, , . .
?
X.Org? dialog,
. dialog ,
, . ,
Midnight Commander dialog ,
(
) dialog .
dialog , Linux.
. , dialog OpenSUSE :
sudo zypper install dialog

Ubuntu apt-get:
sudo apt-get install dialog

dialog .

46

I.

4.2.
, -
. ( 4.1), ,
.
4.1. yes-no
#!/bin/bash
DIALOG=${DIALOG=dialog}
$DIALOG --title " " --clear \
--yesno " /" 10 40
case $? in
0)
echo " ''.";;
1)
echo " ''.";;
255)
echo " ESC.";;
esac

, dialog.
( ) DIALOG --title, --clear,
--yesno. --title , --clear
, --yesno
/. --yesno , , 10 40 .
DIALOG ,
4.1: . , , ( --yesno).
, DIALOG . (
) 0, 1. <Esc>, 255.

. echo . , case 2.
yes-no :
chmod +x yes-no
./yes-no

. 4.1.

4. dialog:

47

. 4.1. yes-no

4.3.
, . OK.
, " OK " ,
. 4.2 . :
\n .
4.2. msg
#!/bin/bash
DIALOG=${DIALOG=dialog}
$DIALOG --title "" --msgbox " ,\n,
Enter" 10 40
case $? in
0)
echo " ";;
255)
echo " Esc";;
esac

. 4.2.
. ,

I.

48

Linux. , -, ,
, - <Enter>. .
, , dialog, .

. 4.2. msg

. , , msgbox, infobox
. - : ,
, . info 4.3, . 4.3.
4.3. info
#! /bin/bash
DIALOG=${DIALOG=dialog}
# -
left=10
#
unit=""
while test $left != 0
do
$DIALOG --sleep 1 \
--title " " \

4. dialog:

49

--infobox " !\n $left


$unit " 10 40
left=`expr $left 1`
test $left = 1 && unit=""
done
# (, ):
# /sbin/reboot

. 4.3. info

4.3, , : sleep? , , , . sleep dialog N , N = 1.

4.4.
read, , ,
, .
input, (. 4.4), 4.4.
4.4. input
#!/bin/bash
DIALOG=${DIALOG=dialog}
tempfile=`tempfile 2>/dev/null` || tempfile=/tmp/test$$
trap "rm -f $tempfile" 0 1 2 5 15

50

I.

$DIALOG --title " " --clear \


--inputbox " ?" 16 51 2> $tempfile
retval=$?
case $retval in
0)
echo " : `cat $tempfile`"
;;
1)
echo " ";;
255)
if test -s $tempfile ; then
cat $tempfile
else
echo " ESC."
fi
;;
esac

. 4.4. ( input)

, ,
. ,
, .
.

4. dialog:

51

4.5.

, ,
. 4.5 menu, ,
(. 4.5). - linuxconf
Red Hat, Mandrake,
.

. 4.5. menu

4.5. menu
#!/bin/bash
DIALOG=${DIALOG=dialog}
tempfile=`mktemp 2>/dev/null` || tempfile=/tmp/test$$
trap "rm -f $tempfile" 0 1 2 5 15
$DIALOG --clear --title "" \
--menu " :" 20 51 4 \
"Full" " " \
"Lite" " (600 )" \
"Restore" " " \
"Update" " 4.0" \
"Reboot" "" 2> $tempfile
retval=$?

52

I.

choice=`cat $tempfile`
case $retval in
0)
echo " '$choice'";;
1)
echo " ";;
255)
echo " ESC.";;
esac

,
, . ,
.

4.6. :

,
. , :
fdisk .
.
, ( 4.6, . 4.6).
4.6. radio
#! /bin/bash
DIALOG=${DIALOG=dialog}
tempfile=`mktemp 2>/dev/null` || tempfile=/tmp/test$$
trap "rm -f $tempfile" 0 1 2 5 15
$DIALOG --backtitle " !" \
--title " " --clear \
--radiolist " " 20 61 5 \
"Manual" " fdisk" off \
"Auto"
" ,
" ON 2> $tempfile
retval=$?
choice=`cat $tempfile`
case $retval in
0)

4. dialog:

53

echo " '$choice'";;


1)
echo " ";;
255)
echo " ESC.";;
esac

, . --backtitle,
,
. radiolist ( ). ()
radiolist checklist:
$DIALOG --title " " --clear \
--checklist " " 20 61 5 \

, ,
on ( ),
off ( ). , () ,
,
. <>.
, . , 4.6 (
checklist radiolist) ,
:
"Manual" "Auto"

. 4.6. radio

54

I.

4.7.
,
, . ,
"
//", , , , .
dialog , (. 4.7 4.8). 4.7
calendar, , .

. 4.7. ()

. 4.8.

4. dialog:

55

4.7. calendar
#!/bin/bash
DIALOG=${DIALOG=dialog}
USERDATE=`$DIALOG --stdout --title "" --calendar " ..." 0
0 1 4 2011`
case $? in
0)
echo " : $USERDATE.";;
1)
echo " .";;
255)
echo " ESC.";;
esac
clear
USERTIME=`$DIALOG --stdout --title " " \
--timebox ",, ..." 0 0 10 00 00`
case $? in
0)
echo " : $USERTIME.";;
1)
echo " .";;
255)
echo " ESC.";;
esac

4.8.
,
, (gauge).
"":
"" 10%. . 4.9 gauge .
4.8. gauge
#!/bin/bash
DIALOG=${DIALOG=dialog}
PCT=10
(
while test $PCT != 110

I.

56

do
echo "XXX"
echo $PCT
echo ": \n\
($PCT %)"
echo "XXX"
PCT=`expr $PCT + 10`
# 1 , 1 10%
sleep 1
done
) | $DIALOG --title "" --gauge "" 20 70 0

. 4.9. ( gauge)

4.9.

(. 4.10). , "". ""
( ) <Enter>, "" . <>,
, <Enter>. , . 4.9
, .
4.9. fselect
#!/bin/bash
DIALOG=${DIALOG=dialog}
FILE=`$DIALOG --stdout --title " " --fselect $HOME/ 10 60`

4. dialog:

57

case $? in
0)
echo " : \"$FILE\"";;
1)
echo " .";;
255)
echo " ESC.";;
esac

. 4.10. ( fselect)

4.10.
dialog Xdialog,
. bash- , . :
, , -

TCL/Tk, ( ,
, Xdialog);
Xdialog ( ,

), . dialog , Xdialog (
) . ,
openSUSE Xdialog : http://www.novell.com/products/
linuxpackages/opensuse/xdialog.html;

I.

58

( ), dialog
, .
Xdialog,
Xdialog :
DIALOG=${DIALOG=Xdialog}

, Xdialog, dialog, :
if [ -z $DISPLAY ]
then
DIALOG=dialog
else
DIALOG=Xdialog
fi

, .
, dialog/Xdialog .
Xdialog (,
exit-box). Xdialog
, .
:
http://dkws.org.ua/mybooks/prg/dialog.tar.gz

II

C
Linux
5.

gcc

6.

7.

8.

/ Linux

, , C, C ,
( ), C
Linux. gcc, ,
.

gcc

5.1.
, . Linux ,
.
UNIX-, Linux,
vi, , . , - "" Linux, , , .
vi , , ? , .
vi 70-
, . vi , 70- . UNIX,
vi, ,
.
, (man vi), : nano, pico, mcedit.
Midnight Commander ( mc),
Norton Commander.
nano mcedit , mc nano. openSUSE Ubuntu:
sudo zypper install mc nano
sudo apt-get install mc nano

mcedit , nano, , . -

5. gcc

61

, .
, :
mcedit < >
nano < >

5.2. gcc
5.2.1.
:
, , ( "" . link).
( DOS/Windows exe/com-) , ( obj), (linker), .
, . , , .
Linux ,
, , .
Linux ( , UNIX- )
. .
, , . :
OpenOffice.org, gcc.
.
, (
):
gcc C (GNU C Compiler);
gcc-c++ gcc C++;
binutils (gprof, as, ld, objcopy,
strings .);

make, automake Makefile (

, );
linux-kernel-headers (

, ),
gcc;

II. C Linux

62

. 5.1. sudo zypper install gcc

glibc-devel , C,

gcc.
. 5.1 gcc OpenSUSE.

5.2.2. Linux
99% , "Hello, world!" . 5.1
, .
5.1. Hello, world! ( hello.c)
#include <stdio.h>
int main(void) {
printf("Hello, world!");
return 0;
}

. 5.2 mcedit.
(, , , mcedit
).
:
gcc hello.c

, . -

5. gcc

63

a.out. , :
./a.out

. !
Linux-!

. 5.2. mcedit


- , , , .

5.2.3.
gcc :
gcc []

gcc , ( man gcc). -o, , a.out


. -v . ,
, -o:
gcc -v -o hello hello.c

64

II. C Linux

-v (. 5.3) . -v : , .
-o hello a.out, . hello :
./hello

. 5.3. -v

C,
, . -l
, :
gcc -ldlib file.c

-l . ( gcc) libdlib.a
, -L. :
-l ( "L") , -L ,
.

5. gcc

65

-nostdlib , , , -L:
gcc -o hello hello.c -L/usr/lib/my -lmylib

static . , , 6.
-I . , , -I:
gcc -I/home/den/include program.c

, -g. ,
gdb,
34.
( "") ,
-g.
,
. -O ( 1),
-O1, -O2, -O3 .
, ,
. -O1 ( -O) . -O2 . 3 (-O3) .
-O1, -O2 -O3 .
-O0 ( ) -O1: , c -O1, 510 , . 35 gprof,
.
. (
,
), "
gcc":
http://gentoo.theserverside.ru/book/ar72.html.

5.3.
5.3.1.
. ,
, . ,

66

II. C Linux

, . ,
, ?
.
, , . , ,
"". , . Linux
( UNIX-)
make. :
Makefile, (, , ). Makefile .
:
make

make Makefile . , clean,


, "" ,
, . .
, . clean
.
make Linux. , , , Linux-,
Linux- ,
Makefile. Makefile
, .
make , automake autoconf. , make.
make :
Makefile make.
, make, ,
. ,
. , , , , .

5.3.2. Makefile
Makefile ,
,
.

5. gcc

67

,
.
,
:
# clean
#
clean:
rm -f *.o

, , :
CC=gcc
...
obj1.o: obj1.c
$(CC) -c obj1.c

,
, CC,
.
Makefile. , . Makefile ( 5.2), ( ).
5.2. Makefile
libmy.so: obj1.o obj2.o
gcc -shared -o libmy.so $^
obj1.o: obj1.c
gcc -fPIC -c $^
obj2.o: obj2.c
gcc -fPIC -c $^
clean:
rm -f libmy.so *.o


-c (),
, . -c , .

libmy.so , obj1.o obj2.o. clean ,


make. clean,
:
make clean

II. C Linux

68

:
libmy.so,
libmy.so,
.
, , -o gcc. ,
libmy.so , main;
,
, obj1.o obj2.o.
obj1.o obj2.o ,
. .
, (. clean);
, -

.
gcc. , clean rm,
6 , ar.
make .
.
!
. Makefile ! ,
, (\t), .

5.2. ,
? Makefile, ( 5.3).
5.3. Makefile
CC=gcc
#
main: first_object second_object
$(CC) -shared -o libmy.so obj1.o obj2.o
# obj1.c
first_object: obj1.c
$(CC) -fPIC -c $^
# obj2.c
second_object: obj2.c
$(CC) -fPIC -c $^
#
clean:
rm -f libmy.so *.o

. main,
first_object second_object. , CC.

5. gcc

69

, , make
:
$^ ;
$@ .

main:
main: first_object second_object
$(CC) -shared -o libmy.so obj1.o obj2.o

libmy.so :
libmy.so: obj1.o obj2.o
gcc -shared -o libmy.so $^

. (libmy.so) $^, , make. 5.2 , .


libmy.so 5.2 :
libmy.so: obj1.o obj2.o
gcc -shared -o $@ $^

, make. make , , :
make main

main . main Makefile, .


Makefile
. , Makefile
gcc, Makefile.intel Intel. make, , -f:
make -f Makefile.intel


++ Intel Linux :
http://software.intel.com/en-us/articles/intel-c-compiler-professional-editionfor-linux-documentation/.

make .
Makefile.
5.2 ( 5.3 ).
make, :

70

II. C Linux

gcc -fPIC -c obj1.c


gcc -fPIC -c obj2.c
gcc -shared -o libmy.so obj1.o obj2.0

rm -f libmy.so *.o ,
clean:
make clean

, gcc, make.
.

.

6.1.
, C, . , , . ,
"" 10 .
, , ( ) , , 1 .

, 11 .
, , 10 50. 21
10 110 .
. ,
printf() C, gcc.
,
-l, :
gcc -o test test. -lmylib

/lib, /usr/lib, /usr/local/lib.


, -L:
gcc -o test test. -L/usr/lib/my -lmylib

lib, . .,
mylib, libmylib.so ( libmylib.a
).
( ). ar, "-

II. C Linux

72

" (, Linux " ",


) a (, libmylib.a).
libmylib.a , , obj1.o, obj2.o, obj3.o, ,
:
gcc -o test test. -lmylib
gcc -o test test. obj1.o obj2.o obj3.o

, , , , , , .
gcc
-shared. "" so. ( ) . , , . .
. obj1.o, obj2.o,
obj3.o , , 20 , 20
"",
.
, , . - ,
, .
, , .

. , .

,
. ()
, , ,
.

, ( "" so, "" a).


?
, , -static, :
gcc -static -o test test.c -lm

6. .

73

, , -static, .

6.2.
, ,
, ar. , Windows ""
"". Windows-
,
, ""
WinZip, WinRAR .
, , (. . ). ar, binutils
( , -
ar). , ( ) , . , tar
ar , gzip bzip . (, tar) .
obj1.o, obj2.o obj3.o, :
ar r libmy.a obj1.o obj2.o obj3.o

,
:
ar x libmy.a

. obj1.c ( 6.1) obj2.c ( 6.2).


6.1. obj1.c
#include <stdio.h>
void hello1 (void)
{
printf("Hello from obj1\n");
}
6.2. obj2.c
#include <stdio.h>
void hello2 (void)
{
printf("Hello from obj2\n");
}

74

II. C Linux

.
make.
Makefile ( 6.3).
6.3. Makefile
libmy.a: obj1.o obj2.o
ar r $@ S^
obj1.o: obj1.c
gcc -c $^
obj2.o: obj2.c
gcc -c $^
clean:
rm -f libmy.a *.o

Makefile : libmy.a,
ar obj1.o obj2.o.
, obj1.o obj2.o ( gcc ). clean .
make :
make

, , , ( 6.4).
6.4. test (test.c)
#include <stdio.h>
int main(void)
{
hello1();
hello2();
return 0;
}

:
gcc -o test test.c -L. -lmy

gcc "" test.c test my ( lib "" ),


(-L.).
test:
./test
Hello from obj1
Hello from obj2

6. .

75

6.3.
. , gcc, ar. ,
obj1.o obj2.o,
.
:
gcc -shared -o libmy.so obj1.o obj2.o

gcc :
gcc -shared -o _ __

, , -shared.
, , "". , , , .
,
-fPIC,
- (Position Independent Code). ,
.
. -L,
, . ,
.
, .
/home/den/mylibs:
gcc -o test test.c -L/home/den/mylibs -lmy

, /home/den/mylibs . :
,
libmy.so, . 99%
/home/den/mylibs, libmy.so,
(LD_LIBRARY_PATH).
, /etc/ld.so.conf LD_LIBRARY_PATH.
, ? :
, /etc/ld.so.conf

, ;
/etc/ld.so.conf , -

/etc/ld.so.conf
( /etc/ld.so.cache).

II. C Linux

76

, .
X11, GTK, Qt . .
, ,
, .
-W1 ( , -rpath) -rpath ( ).
, /usr/lib/my ""
/etc/ld.so.conf. :
gcc -o test test.c -L/usr/lib/my -lmy -W1,-rpath,/usr/lib/my

, .
test.c ( test). ,
my ( libmy.so),
/usr/lib/my, , "" , /home/den/mylibs,
(, libmy.so). -W1 . ,
. -W1: , ld ( -rpath),
( -rpath ).
, , ld.so.conf, /usr/lib
/usr/local/lib, :
gcc -o test test.c -lmy

, .

, ld.so.conf, "" . ld.so.cache ldconfig, root.
man ldconfig.

Makefile, ( 6.5).
6.5. Makefile
libmy.so: obj1.o obj2.o
gcc -shared -o libmy.so $^
obj1.o: obj1.c
gcc -fPIC -c $^

6. .

77

obj2.o: obj2.c
gcc -fPIC -c $^
clean:
rm -f libmy.so *.o

Makefile , (. 6.3). :
libmy.so, libmy.a;
gcc -shared, ar;
-fPIC.

, :
: -

, "" ;
: , ,
. ;
.


7.1.
? ,
, . ,
. , ,
, . ? . Linux , , , /etc.
.
.
.
Linux, Windows, Windows
, UNIX , , .
, , , . .

7.2. ?
, . , (, , , ).
.
. ,
bash, . mc, Midnight Commander, ( ) bash. , bash
( ).

7.

79

, . . , . init (, Linux ). Linux init


( init ). , init, init .
=, ,
=, . , . .
, , USER ( ) HOME
( ).
env. , :
USER (,

);
HOME ;
PWD () ;
SHELL ( bash);
PATH .

:
echo $

:
=

:
FIRSTPRG=hello
echo $FIRSTPRG

,
. , :
export FIRSTPRG

:
export FIRSTPRG=hello

( ),
. , ,

80

II. C Linux

"" . (
, 2 3). , : ,
. ,
- . , , , " ". ,
.

7.3.

.
environ, unistd.h.
getenv().
, getenv(). . environ , . . =
, (. . ) ,
.
.
getenv() . :
char * getenv (char * VAR_NAME);

, ( 7.1).
7.1. user.c
#include <stdio.h>
int main (void)
{
value = (char*) getenv("USER");
printf(" : %s\n", value);
return 0;
}

: USER value, .

7.

81

7.4.
:
setenv() -

;
putenv() , setenv(), -

=;
unsetenv() .

stdlib.h. . setenv():
int setenv (const char * NAME, const char * VALUE, int OV);

, ( )
NAME, VALUE. OV
. 0, NAME , , 0, NAME VALUE.
setenv() 0,
, 1 .
putenv() ,
= ( , NAME,
, VALUE setenv()). :
int putenv (char * INITSTR);

:
result = putenv("DIR=/etc");

setenv(), 1 0,
. , putenv() UNIX , .
unsetenv() NAME :
int unsetenv(const char * NAME);

, .
( 7.2).
7.2.
#include <stdio.h>
#include <stdlib.h>

II. C Linux

82

int main (void)


{
putenv("DIR=/etc");
setenv ("DIR", "/home/den", 1);
value = (char*) getenv("DIR");
printf("DIR = %s\n", value);
unsetenv("DIR");
return 0;
}

putenv() DIR ( /etc).


( OV) setenv().
getenv() . unsetenv() .
, . , UNIX-,
:
int clearenv(void);

, . .
, .

environ NULL, ,
, .
clearenv() , .

/ Linux
8.1. /.
/

/ (Input/Output, I/O) . , / (
) ( ). ,
/.
/ : C Linux.
. , ,
, C. c Windows. , .
, Linux.
/ . ,
, (
),
, . . Linux, ,
.
/,
/ . ,
Linux-, ,
.
/
. ,
ifconfig

84

II. C Linux

, ,
. ( ps ax)
grep, .
:
echo "some text" > file.txt

> , , ,
, , .
ifconfig .
:
ifconfig > ifconfig.txt

> >>, , :
echo "some text" > file.txt
echo "more text" >> file.txt
cat file.txt
some text
more text

> >> /
|. ,
big_text:
cat big_text

big_text , . , cat - , , :
cat big_text | more

, , less:
less big_text

. , file.txt
:
echo y | rm file.txt

rm ( <Y>),
echo.
. ,
, 555-555. , :
cat file.txt | grep "555-555"

8. / Linux

85

Linux
(. . ), . ,
/, . :
gcc 2>gcc.errors

gcc gcc.errors.
? ! gcc.errors
:
gcc: no input files

8.2. C
/
/ :
, ,
.
C FILE :
FILE * file1;

, :
extern FILE * stdout;
/* */
extern FILE * stdin; /* */
extern FILE * stderr; /* */

, /. / Linux /. ,
(, . .),
.
:
FILE * fopen (const char * FLOCATION, const char * OPEN_MODE);
FILE * freopen (const char * FLOCATION, const char * OPEN_MODE, FILE * FP);
FILE * fclose (FILE *FP);

, ,
. fopen() ,
, . FP , ,
. FP.
:

86

II. C Linux

int fgetc (FILE * FP);


int fputc (int byte, FILE * FP);

FP, byte
FP.
, , :
char * fgets (char * STR, int SIZE, FILE * FP);
int fputs (const char * STR, FILE * FP);
int fprintf(FILE * FP, const char * FMT, ...);
int fscanf (FILE * fp, const char * FMT, ...);
int vfscanf (FILE * FP, const char * FMT, va_list ap);
int vfprintf (FILE * FP, const char * FMT, va_list ap);

, . fgets() fputs() FP . SIZE fgets() STR.


fprintf() fscanf() printf() scanfs(), /, . vfscanf()
vfsprintf() C99.
fprintf() fscanf(), .
va_list, stdarg.h.
/ , /.
. / , / . , .
C :
#define SEEK_SET 0
/* */
#define SEEK_CUR 1
/* */
#define SEEK_END 2
/* */
typedef struct {...} fpos_t;
int fseek (FILE * FP, long int OFFSET, int ORIGIN);
int fgetpos (FILE * FP, fpos_t * POSITION);
int fsetpos (FILE * FP, fpos_t * POSITION);
long int ftell (FILE * FP);
void rewind (FILE * FP);

fseek() . , ( )
(ORIGIN). ( )
: SEEK_SET, SEEK_CUR, SEEK_END.

8. / Linux

87

fgetpos() :
FILE *fp;
fpos_t f_location;
...
fgetpos(fp, &f_location);

fsetpos() . fgetpos():
fsetpos(fp, &f_location);

ftell() FP,
, . ftell() 1.
, rewind(), . stdio.h.
, C
/, fflush(), / . fflush() , .
fflush() , .
fflush() :
int fflush(FILE * stream);

. , ( 8.1).
8.1.
#include <stdio.h>
#include <stdlib.h>
int main (int argc, char * argv[])
{
FILE *fp;
char c;
if ((fp=fopen(argv[1], "r"))==NULL) {
printf(" \n");
exit(1);
}
while ((ch=fgets(fp)) != EOF) {
printf("%c", ch);
}

II. C Linux

88
fclose(fp);
return 0;
}

, ,
. C. , -
.
( 8.2).
8.2. stdcopy.c
#include <stdio.h>
#include <stdlib.h>
int main (int argc, char *argv[] )
{
FILE *in, *out;
char *ch;
if (argc!=3) {
printf(": stdcopy in-file out-file\n");
exit(1);
}
if(in=fopen(argv[1], "rb"))==NULL) {
printf(" \n");
exit(1);
}
if(out=fopen(argv[2], "wb"))==NULL) {
printf(" \n");
exit(1);
}
while(!feof(in)) {
ch = fgetc(in);
if(ferror(in)) { printf(" \n"); break; }
else {
if(!feof(in)) putc(ch, out);
if(ferror(out)) { printf(" \n"); break; }
}
}
fclose(in);
fclose(out);
return 0;
}

8. / Linux

89

: . .

8.3. /
8.3.1. /
C /. . Linux ( FILE) .
, .
, .
.
ulimit -n, bash, ksh . csh tcsh limit descriptors.
open(), creat()
close():
int
int
int
int

open (const char * FNAME, int OFLAGS, mode_t MODE);


open (const char * FNAME, int OFLAGS);
creat (const char * FNAME, mode_t MODE);
close (int FD);

:
ssize_t
ssize_t
ssize_t
ssize_t

read (int FD, void * BUFFER, size_t SIZE);


write (int FD, const void * BUFFER, size_t SIZE);
readv (int FD, const struct iovec * VECTOR, int SIZE);
writev (int FD, const struct iovec * VECTOR, int SIZE);


lseek():
off_t lseek (int FD, off_t OFFSET, int WHENCE);

, Linux.
. ,
Linux (. 8.1). . 8.1
,
.
C .
Linux,
Linux. Linux
, .

II. C Linux

90

8.1. Linux

S_IFREG

,
.
, (,
, )

S_IFBLK

Linux
( 14).
, .

S_IFCHR

.
,

S_IFDIR

,
, . 15

S_IFLNK

S_IFSOCK

.
, : Web-
Linux FreeBSD,
Windows MacOS

FIFO

S_IFIFO

. FIFO 12

C
, ( ),
Linux.
Linux (16 ), (. 8.2). (file mode) (permissions), :
.
8.2. Linux

08

911

1215

8. / Linux

91

. Windows- Linux, 18. ,


.
: (, ),
(, ) . root , .
(, ) : , .
, . ,
.
, , .
,
. , .
, sys/stat.h. . 8.3.
8.3.

S_IXOTH

S_IWOTH

S_IROTH

S_IXGRP

S_IWGRP

S_IRGRP

S_IXUSR

S_IWUSR

S_IRUSR

, "" . 8.3 . . 8.4


( 18,
).
. 8.5 . C, .

II. C Linux

92

8.4.

S_ISUID

SUID

S_ISGID

SGID

S_ISVTX

""

8.5.

O_RDONLY

O_WRONLY

O_RDWR

O_APPEND

O_ASYNC

SIGIO, /

O_CREAT

O_DIRECT

,
,

O_DIRECTORY

O_EXCL

O_NOFOLLOW

O_NONBLOCK

O_NOATIME

O_SYNC

/:
write()

O_TRUNC

0, ,

, . :
S_IXUSR | S_IWUSR

8.3.2. creat()
creat(),
fcntl.h:
int creat (const char * FILENAME, mode_t MODE);

8. / Linux

93

, . 1 : . , creat() ( 8.3).
8.3.
#include
#include
#include
#include
#include

<stdio.h>
<fcntl.h>
<sys/types.h>
<sys/stat.h>
<unistd.h>

int main (void)


{
int fdesc;
mode_t modes = S_IRUSR | S_IWUSR;
fdesc = creat("test.txt", modes);
if (fdesc == -1) {
fprintf(stderr, " \n");
return 1;
}
close(fdesc);
return 0;
}

test.txt:
.
, :
stderr.

close(), unistd.h.
write(), read(), lseek()
SEEK_CUR, SEEK_SET SEEK_END.
fcntl.h ,
open() O_RDONLY, O_WRONLY .
(S_IRUSR, S_IWUSR) sys/stat.h. sys/types.h
.

8.3.3. : open() read()


C fopen() ,
. /
: (creat),
(open).

II. C Linux

94

, , ,
, .
,
, . . . 8.5.
open() :
int open (const char * FILENAME, int FLAGS, mode_t MODE);
int open (const char * FILENAME, int FLAGS);

, ,
. .
read() unistd.h, :
ssize_t read (int FD, void * BUFFER, size_t SIZE);

, , ( ). SIZE ( ) , .
read() :

SIZE: , 100 ,
;
0 ;
1 .

, ( 8.4).
8.4.
#include <stdio.h>
#include <fcntl.h>
#include <unistd.h>
int main (void)
{
int fd;
char c;
fd = open("test.txt", O_RDONLY);
if (fd == -1)
{
fprintf(stderr, " \n");
return 1;
}

8. / Linux

95

while (read (fd, &c, 1) > 0) printf("%c", c);


close(fd);
return 0;
}

,
, . . .
, ,
4096 . , 4
4096 !

8.3.4. write()
write() ,
write() unistd.h:
ssize_t write (int FD, const void * BUFFER, ssize_t SIZE);

, FD, BUFFER, SIZE . 1 .


stdcopy.c,
C. (syscopy.c), , Linux ( 8.5).
8.5. syscopy.c
#include
#include
#include
#include

<stdio.h>
<unistd.h>
<fcntl.h>
<sys/types.h>

int main (int argc, char ** argv)


{
/* 4096 */
char buffer [4096];
/* */
int fin, fout;
ssize_t r;

/* - */

/* */
if (argc < 3) {
fprintf(stderr, ": syscopy in out\n);
return 1;
}

II. C Linux

96

/* */
fin = open (argv[1], O_RDONLY);
if (fin == -1) {
/*
*/
printf(" : %s\n", argv[1]);
return 1;
}
/* */
fout = open(argv[2], O_WRONLY | O_CREAT | O_TRUNC, 0640);
if (fout == -1)
{
printf(" : %s\n", argv[2]);
return 2;
}
/* */
while ((r = read(fin, buffer, 4096)) > 0)
write(fout, buffer, r);
/* */
close(fin);
close(fout);
return 0;
}

: (
), : fin ( ) fout (
). .
, :
fout = open(argv[2], O_WRONLY | O_CREAT | O_TRUNC, 0640);

(O_WRONLY), (O_CREAT)
, (O_TRUNC). 0640: ,
,
. 18.
while 4
. write() . .
,
write(). .

8. / Linux

97

stdout ( 1) stderr ( 2). :


write(2, "Error", 5);

8.3.5. lseek()
lseek() /.
unistd.h :
off_t lseek(int FD, off_t OFFSET, int ORIGIN);

, , ORIGIN. ORIGIN :
SEEK_SET ;
SEEK_CUR /;
SEEK_END .

lseek() 1, ,
/ .
Linux , ""
,
lseek() :
/* "" */
lseek(fd, 0, SEEK_SET);
/* */
off_t position = lseek(fd, 0, SEEK_CUR);

, .

98

II. C Linux

III


9.

10.

11.

12.

13.

.
, , ,
, .
, ,
"" , .


9.1. Linux
9.1.1.
, Linux .
. ,
, .
init (, Linux
).
mc, Midnight Commander,
( )
bash. , bash ( ).
Linux init ( init
). , init, init .
Linux
(PID, Process ID). init 1.
ID , ,
. , .
, , .
ps.
, ps -e --forest. ps
(. 9.1). , , pstree,
(. 9.2). , ,
:
pstree | less

9.

. 9.1. ps -e --forest

. 9.2. pstree

101

III.

102

ps . 9.1.
9.1. ps

-a

,
( )

-e

-t _

-u _

-g _

-x

9.1.2.
, - , mc.
( , - ), . ("") kill. :
kill [] PID

PID (Process ID) ,


; . (
), .
ps. , mc . , , ( <Alt>+<F2>). , ps. ,
, bash ps (. 9.3).
(mc), ,
ps -a ps -U root. , , ,
( , root).
mc ps (. 9.4),
(root) . , ps (tty1), .
,
. TTY (?). (,

9.

103

, ), ps
: pts/N, N .
, PID , "":
# kill 2484

. 9.3.

. 9.4. PID mc

104

III.

mc
. ps -a, mc .
PID :
# ps ax | grep <>

, # ps ax | grep firefox.
-, , PID , , ps.
, , :
# killall < >

, .
, mc,
"", mc. killall ""
.
kill killall ,
, ,
. root, .
kill , , xkill, "" .
xkill, ,
(, , ""?).
, , .
kill, ,
, , ( , kill).
, . :
bash
sleep 1m &
ps -f

bash.
(
&) 1 ( ).
. PPID (Parent
PID) . sleep
2048.
exit, bash,
sleep.
ps -f sleep: 1.
, "" sleep
init (. 9.5).

9.

105

. 9.5.

. (
) .

9.1.3. top:

, ,
.
, - ,
top (. 9.6) . ,
, . , - "".
. 9.6 , (0,3%)
top. , . top , <Q>. <Q>
:
<U> (. . , , );
<D> ;
<F> , . %CPU, . . , ;
<H> top.

III.

106

. 9.6. top

top . 9.2.
9.2. top

PID

USER

PR

NI

nice (. . 9.1.4)

VIRT

, ( )

RES

,
( ).
, . . RES = CODE + DATA

:
R ;
S "" ( ), ;
D " " (uninterruptible sleep), ;
T ;
Z () ,
,

%CPU

%MEM

9.

107
9.2 ()

TIME+

COMMAND

, ( )

9.1.4. nice renice:



, . , .
nice
. , , . :
nice -n <>

20, 19. 10.


,
renice:
renice n <> -p PID

9.2. system()
, . system().
system(), fork(),
, /bin/sh.
system() stdlib.h. :
int system(const char * COMMAND);

COMMAND , . system() 0, .
system() 0, .
( 9.1).
9.1. system()
#include <stdio.h>
#include <stdlib.h>

108

III.

int main(void)
{
system("sleep 30");
printf("After sleep\n");
return 0;
}

. system() , "After sleep" 30 .


, , &
:
system("sleep 30 &");

COMMAND , , :
system("mcedit /etc/passwd");
system("cd /");

system() , ,
fork() exec(),
.

10



10.1.
10.1.1.
, system()
, .
fork()
exec().
fork(),
.
"" Multics. .
. , . , , , , .
UNIX- . : , . .
,

. .
, , .

, . - , - .
.

, .
"" -

110

III.

, , .
.
, , " " .
, : ", <>".
.
. , .
<Enter> - .
<Enter>. , ,
, , . , . ( )
, "", .
, .
,
,
. ,
, , .
,
, "" .
. . : (. .
- ), . ,
.
: ,
.
. :
.
, Z top.
.
. 10.1.
, . . ,
,
.
. .

10.

111

. 10.1.

:
;
;
-

;
;
;
.
,
, , .

10.1.2. fork()
Linux , ,
. -
( ) "" .
,
12, .
Linux SMP (Symmetric Multiprocessor
Architectures). SMP
Linux. Linux ( 11), . , , "" , .
"" .
() . , .

112

III.

"" ,
, .
. 11.
, . , , .
. , () .
(entry point).
C- main().
main().
, fork(). , , .
: fork() , . execl().
fork() .
execl().
. ( 10.1).
10.1. fork-demo.c
#include <unistd.h>
#include <stdio.h>
int main (void)
{
fork();
sleep(30);
return 0;
}

:
gcc -o fork-demo fork-demo.c
./form-demo

ps. fork-demo.
,
.
: ( 10.2). : fork() 0, 1 .

10.

113

10.2. fork-demo2.c
#include <sys/types.h>
#include <unistd.h>
#include <stdio.h>
int main (void)
{
if (fork() == 0)
printf(" , PID= %d\n", getpid());
else
printf(" , PID= %d\n", getpid());
return 0;
}

fork-demo : ,
. ,
: Linux ,
, .

10.1.3. exec
(,
, , ,
). .
. , unistd.h:
int
int
int
int
int
int

execl (const char * PATH, const char * ARG, ...);


execle (const char * PATH, const char * ARG, ..., const char ** ENVP);
execlp (const char * FILE, const char * ARG, ...);
execv (const char * PATH, const char ** ARGV);
execvp (const char * FILE, const char ** ARGV);
execve (const char * PATH, const char ** ARGV, const char ** ENVP);

, ( 10.3).
10.3. (exec.c)
#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>

III.

114
int main (void)
{
char * args[] = {
"ls",
"/",
NULL
};
pid_t r = fork();
if (r == 0) {
execve("ls", args, NULL);
}
return 0;
}

, fork().
execve() ls. args , . . (NULL).
: environ, , . ( 10.4).
10.4. environ
#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
extern char ** environ;
int main (void)
{
char * args[] = {
"ls",
"/",
NULL
};
pid_t r = fork();
if (r == 0) {
execve("ls", args, environ);
}
return 0;
}

10.

115

10.3, . environ,
execve().
( 10.5). ,
, =.
10.5.
#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
int main (void)
{
char * args[] = {
"program",
"/",
NULL
};
char * envp [] {
"USER=den",
"HOME=/home/den",
NULL
}
execve("./program", args, envp);
return 0;
}

exec.
, .
execve():
int execve (const char * PATH, const char ** ARGV, const char ** ENVP);

: , .
. ,
, /bin/bash.
, . , , . NULL. , -

III.

116

/usr/bin/program arg1 arg2. :


char * args[] = {
"/usr/bin/program",
"arg1",
"arg2",
NULL
};

. "=" (. 7). NULL.


execl() execve() , , . (
) . ( ):
int execl (const char * PATH, const char * ARG, ...);

:
execl("/usr/bin/program", "/usr/bin/program", "arg1", "arg2", NULL);


,
. 0, 0 .
0 , : , .

execlp() execl(), ,
, , PATH:
int execlp (const char * FILE, const char * ARG, ...);

:
execlp("program", "program", "arg1", "arg2", NULL);

execle() execl(), :
int execle (const char * PATH, const char * ARG, ..., const char ** ENVP);

execvp() execv() execve(), , , . , execv()


,
execvp() :

10.

117

int execv (const char * PATH, const char ** ARGV);


int execvp (const char * FILE, const char ** ARGV);

:
execv("/usr/bin/program", args);
execv("program", args);

10.2. wait():

, .

. , - .
: .
. .

system(), .
wait(), , .
wait():
#include
#include
#include
#include
#include
...
int pid;

<stdio.h>
<unistd.h>
<sys/types.h>
<stdlib.h>
<wait.h>

unsigned short status;


...
if((pid = fork()) == 0 ){
/* */
execl(....);
perror("exec "); exit(1);
}
/* */
while((pid = wait(&status)) > 0 )
printf(" pid=%d %d\n",
pid, status >> 8);
printf( " \n");

118

III.

, . wait.h. fork() .
- execl()
exec. , - ( 0,
). ,
perror() (
printf() ).
, -
, exit() 1.
(
?). wait() PID
, status (
, "" ). .
. while(), :
while((pid = wait(&status)) > 0){
if( WIFEXITED(status)){
printf( " %d %d\n",
pid, WEXITSTATUS(status));
} else
if( WIFSIGNALED(status)){
printf( " %d %d\n",
pid, WTERMSIG(status));
if(WCOREDUMP(status))
printf( "Core dumped\n" );
} else if( WIFSTOPPED(status)){
printf(" %d %d\n",
pid, WSTOPSIG(status));
} else if( WIFCONTINUED(status)){
printf( " %d \n",
pid);
}
}

:
WIFEXITED() , -

return main
ext();
WEXITSTATUS .

, WIFEXITED() ;

10.

119

WIFSIGNALED() , "" -

;
WIFSTOPPED() ,

( !) ;
WCOREDUMP() , ,

core, gdb ;
WCONTINUED() .

, , , .

10.3.
, ,
fork(). wait() -.
exec*().
-
exit(). . - .
. , , PID
.
den, ,
, , . root,
.
, signal():
signal(snum, function);

(. ), , .
SIG_IGN, . .
signal():
#include <signal.h>
...
signal(SIGTTIN, SIG_IGN);
signal(SIGHUP, signal_handler);

kill():
kill(pid, snum);

120

III.

PID , ,
( ). signal.h. .
SIGHUP ( 1) ,

.
, .
hung up . , ,
. . -, , .
SIGINT ( 2) , (-

: , )
<Ctrl>+<C> ( ).
SIGKILL ( 9) , -

.
SIGSEGV ( 11) , -

, . , ,
(core).
SIGTERM ( 15) "" . -

, ( , ). , (
) .
SIGCHLD ( 17) , -

. .
SIGCONT ( 18) , -

SIGSTOP.
SIGSTOP ( 19) .

.
SIGTSTP ( 20) ,

<Ctrl>+<Z>.

10.4.
:
PID (Process ID) . ;
PPID (Parent PID) ;
UID (User ID) () , .

,
unistd.h:

10.

121

pid_t getpid (void);


pid_t getppid (void);
uid_t getuid(void);

pid_t uid_t sys/types.h.


, PID ,
:
#include <unistd.h>
#include <sys/types.h>

, getuid() .
( /etc/passwd),
getpwuid(), pwd.h:
struct passwd * getpwuid (uid_t UID);

passwd , pw_name, :
#include <unistd.h>
#include <sys/types.h>
#include <pwd.h>
#include <stdio.h>
#include <stdlib.h>
...
// UID
uid_t uid = getuid();
//
struct passwd * p = getpwuid(uid);
if (p == NULL)
{
printf("Error\n");
return 1;
}
printf("Username: %s", p->pw_name);

11


11.1.
, (, threads) . , ,
. "" ,
,
.
- ,
fork(), ,
.
fork() ,
, .
PID . ,
, 10.2. 11.1.
11.1. : vs
#include <sys/types.h>
#include <unistd.h>
#include <stdio.h>
int main (void)
{
int count = 0;
if (fork() == 0) {
count++;

11.

123

printf(" , count = %d\n", count);


return 0;
}
else
printf(" , count = %d\n", count);
return 0;
}

, count count : Linux .


, (IPC),
.
: ,
,
.
, .
,
(PID). (THREAD_ID),
.
, . : .
Linux ,
, .
Linux :
, ;
pthread_create() ,

.
.

pthread_create().

Linux pthread. , -lpthread.

11.2. pthread_create()
pthread_create():
int pthread_create(pthread_t * THREAD_ID, void * ATTR,
void *(*THREAD_FUNC) (void*), void * ARG);

III.

124

, . . Linux
, , - NULL .
, ,
.
, ( 11.2).
11.2. threads.c
#include <stdio.h>
#include <unistd.h>
#include <pthread.h>

/* */

void * thread1 (void)


{
printf("\n 1\n");
sleep(5);
/* 5 */
}
void * thread2 (void)
{
printf("\n 2\n");
sleep(10);
/* 10 */
}
int main (void)
{
pthread_t tid1;
pthread_t tid2;

/* */
/* */

/* */
pthread_create (&tid1, NULL, &thread1, NULL);
/* */
pthread_create (&tid2, NULL, &thread2, NULL);
while (1);
return 0;

/* */

thread1()
thread2(). ,
pthread_create() NULL. -

11.

125

pthread() main(), thread1() thread2(),


.
while(). ,
main() . <Ctrl>+<C>.
,
, .
, -lpthread. , , pthread_create(), (
). :
void * thread1 (void * args)
...
void * thread2 (void * args)

,
, 11.2. . threads.c :
void * thread1 (void)
{
printf("\n 1\n");
sleep(5);
/* 5 */
return NULL;
}
void * thread2 (void)
{
sleep(10);
/* 10 */
printf("\n 2\n");
return NULL;
}

.
"" 5 . 10 ,
. ,
, . , "" : void, , NULL.
:
void * thread1 (void)
{
printf("\n 1\n");
sleep(5);
/* 5 */
exit(1);

III.

126
}

void * thread2 (void)


{
sleep(10);
/* 10 */
printf("\n 2\n");
return NULL;
}

"", exit()
, . . , 5 . . ,
, , .

11.3.

threads.c ,
. , ( 11.3).
11.3.
#include <stdio.h>
#include <unistd.h>
#include <pthread.h>

/* */

void * thread1 (void * arg)


{
int c = *(int*) arg;
printf("\nThread 1: %d\n", c);
sleep(5);
/* 5 */
return NULL;
}
void * thread2 (void * arg)
{
int c = *(int*) arg;
printf("\nThread 2: %d\n", c);
sleep(10);
/* 10 */
return NULL;
}
int main (void)

11.

127

{
pthread_t tid1;
pthread_t tid2;
int t_arg;

/* */
/* */

t_arg = 10;
/* */
/* */
pthread_create (&tid1, NULL, &thread1, &t_arg);
t_arg = 50;
/* */
/* */
pthread_create (&tid2, NULL, &thread2, &t_arg);
while (1);
return 0;

/* */

. 11.1.
, .

. 11.1.

.
, . , (,
) ( 11.4).

III.

128

11.4.
#include <stdio.h>
#include <unistd.h>
#include <pthread.h>

/* */

struct t_args
{
int arg1;
int arg2;
}
void * thread1 (void * arg)
{
struct t_args t = *(struct t_args*) arg;
printf("\nThread 1: %d %d\n", t.arg1, t.arg2);
sleep(5);
/* 5 */
return NULL;
}
int main (void)
{
pthread_t tid1;
struct t_args ta;

/* */

/* */
ta.arg1 = 10;
ta.arg2 = 50;

/* */
pthread_create (&tid1, NULL, &thread1, &ta);

while (1);
return 0;

/* */

, .

11.4. :
pthread_exit()
(return) main,
exit(). exit() ,
. , -

11.

129

pthread_exit(),
pthread.h:
void pthread_exit (void * RESULT);

RESULT . ,
.
pthread_exit():
void * thread1 (void * arg)
{
struct t_args t = *(struct t_args*) arg;
printf("\nThread 1: %d %d\n", t.arg1, t.arg2);
sleep(5);
/* 5 */
pthread_exit(NULL);
}

11.5. :
pthread_join()

. while, ,
.
. , .
while() : while .
, , 1. while :
1, (break). ,
. 11.5.
11.5. "" while
#include <stdio.h>
#include <unistd.h>
#include <pthread.h>
int end = 0;

/* */

/* , */
void * thread1(void * arg)
{
int c = *(int*) arg;
printf("\nThread 1: %d\n",c);
sleep(5);

III.

130

/* 1 */
end = 1;
return NULL;
}
int main (void)
{
pthread_t tid1;
int t_arg;
t_arg = 10;
/* */
pthread_create(&tid1, NULL, &thread1, &t_arg);
/* , end 1.
, end
1 */
while (end!=1);
return 0;
}

: ,
, .
while, pthread_join().
, ,
pthread_join().
pthread_join() "" .
, , :
int pthread_join (pthread_t THREAD_ID, void ** DATA);

,
THREAD_ID. , pthread_exit().
,
, . pthread_join(), .
, pthread_join(). , .
: - ,

11.

131

. , , pthread_join().
pthread_join() , .
pthread_join() , .
pthread_join(),
.
, .
pthread_exit().
"" , ( 11.6).
11.6.
#include <stdio.h>
#include <unistd.h>
#include <pthread.h>
void * thread1(void * arg)
{
int c = *(int*) arg;
c = c * c;
sleep(5);

/* */
/* */
/* ""
*/

/* */
pthread_exit((void *)c);
}
int main (void)
{
pthread_t tid1;

/* */

/* t_arg , ,
t_res
*/
int t_arg, t_res;
t_arg = 10;
/* */
pthread_create(&tid1, NULL, &thread1, &t_arg);

III.

132

/* */
pthread_join(tid1,(void *) &t_res);
/* */
printf("\nResult = %d\n", t_res);
return 0;
}

11.6.
getpid(), .
pthread_self(), :
pthread_t pthread_self (void);

? : , pthread_join()
. ==,
pthread_equal():
if (!pthread_equal(pthread_self(), tid))
pthread_join(tid, &t_res);

11.7.
""
,
pthread_cancel():
int pthread_cancel(pthread_t THREAD_ID);

0, .
pthread_cancel()
.
, Linux .
. :
man
man
man
man
man
man
man

pthreads
pthread_create
pthread_cancel
pthread_join
pthread_exit
pthread_equal
pthread_self

12


12.1.
"" , . . . - - ,
. IPC InterProcess Communication.
Linux :
;
FIFO (First In First Out);
;
;
;
.

UNIX, ,
UNIX : System V BSD. ,

System V AT&T. Linux .

12.2.

.
UNIX.
( ). ,

134

III.

. .
.
8 /.
, :
cat some_big_file | less

/ , . .
. . / popen():
FILE * popen(const char *command, const char *type);

, (
). . r, ; ,
w.
wr, , ,
, .
popen() FILE NULL,
. pclose() /.
fflush(), - .
popen() 12.1. , ls . ls . ls ,
.
12.1. popen()
#include <stdio.h>
int main() {
FILE *in;
extern FILE *popen();
char buff[512];
/* , ls, "r" */
if (!(in = popen("ls", "r"))) {
exit(1);
}

12.

135

/* ls */
while (fgets(buff, sizeof(buff), in) != NULL ) {
printf(": %s\n", buff);
}
/* */
pclose(in);
}

, ,
.
. parent ( )
child ( ). , , , ,
.
12.2.
12.2. parent.c
#include
#include
#include
#include

<stdio.h>
<sys/wait.h>
<unistd.h>
<stdlib.h>

int main()
{
char buff[1024]={0};
FILE * child;
int sta tus;
/* .
/usr/local/bin/child
*/
child = popen("/usr/local/bin/child", "w");
if (!child)
{
printf(" \n");
exit(1);
}
printf(" : " );
/* */
fgets(buff, sizeof (buff), stdin);
/* */
fprintf(child, "%s\n", buff);

III.

136

/* */
fflush(child);
// pclose()
status=pclose(child);
if (!WIFEXITED(status))
printf(" \n");
printf(" \n");
return 0;
}

( w).
, ( 12.3).
child.c, child
/usr/local/bin. child.c : . 12.2.
fflush(). ""
. fflush() .
12.3. child.c
#include <stdio.h>
int main()
{
char buff[1024]={0};
fgets(buff, sizeof (buff), stdin);
printf(" : %s\n",buff);
printf(" \n");
return 0;
}

:
gcc -o parent parent.c
gcc -o child child.c

child /usr/local/bin:
sudo cp ./child /usr/local/bin/child

./parent. (123456
):

12.

137

: 123456
: 123456

12.3. FIFO
FIFO (First In First Out).
: " , ".
FIFO ,
:
FIFO ,
;
,
: FIFO- ;

. .
, : FIFO- , .
FIFO-
mknod(). :
sudo mknod FIFO p
sudo mkfifo a=rw FIFO

FIFO. mknod :
int mknod( char *pathname, mode_t mode, dev_t dev );

mknod() , , , . mknod FIFO-,


mknod():
#include
#include
#include
#include
...

<sys/types.h>
<sys/stat.h>
<fcntl.h>
<unistd.h>

mknod("FIFO", S_FIFO|0666, 0);

FIFO- ,
.
. ,
.

III.

138

:
S_IFREG ( );
S_IFCHR ;
S_IFBLK ;
S_IFIFO ;
S_IFSOCK .

0, , 1, . errno, :
EFAULT, ENOTDIR, ENOENT ;
EACCESS ;
ENAMETOOLONG .

mknod man 2 mknod. (dev) , .


FIFO
0666.
UMASK
Linux
, . ,
umask(). ( , , , ), umask(0), . . 0, , :

umask(0);
mknod("FIFO", S_FIFO|0666, 0);

. ,
. FIFO-
, ( , ). , ,
<Ctrl>+<C>.
12.4, 12.5.
12.4. fifo-read.c
#include <stdio.h>
#include <stdlib.h>
#include <sys/stat.h>

12.

139

#include <unistd.h>
#include <linux/stat.h>
/* */
#define FIFO
"FIFO"
void main(void)
{
FILE *fp;
/* */
char buf[128];
/* FIFO 0666.
, */
umask(0);
mknod(FIFO, S_IFIFO|0666, 0);
/* */
while(1)
{
fp = fopen(FIFO, "r");
fgets(buf, 128, fp);
printf(": %s\n", buf);
fclose(fp);
}
}

12.5. ,
, . , 12.5.
12.5. fifo-write.c
#include <stdio.h>
#include <stdlib.h>
#define FIFO

"FIFO"

void main(int argc, char *argv[])


{
FILE *fp;
if ( argc != 2 ) {
printf(": fifo-write <>\n");
exit(1);
}

III.

140
fp = fopen(FIFO, "w");
fputs(argv[1], fp);
fclose(fp);
}

:
gcc -o fifo-read fifo-read.c
gcc -o fifo-write fifo-write.c

:
./fifo-read

(<Alt>+<F2>, ) fifo-write:
./fifo-write test

( fifo-read),
:
: test

, , ?
: fifo-write , . ,
, ,
.
: ,
"", . . fifo-read , ""
( fifo-write) SIGPIPE.

12.4.
12.4.1. System V
, , (IPC) System V.
, IPC , . , . , , . . 123
, 123.
, (IPC Key). - -. , ftok():

12.

141

# include <sys/types.h>
# include <sys/ipc.h>
key_t ftok( char *pathname, char proj );

1, . ,
, .
inode (
, inode ) , . - ,
. :
key_t key_ipc;
key_ipc = ftok ("/etc/passwd", 'd');

IPC ipcs. , , IPC,


:
------ Shared Memory Segments -------key
shmid
owner
perms

bytes

nattch

------ Semaphore Arrays -------key


semid
owner
perms

nsems

status

------ Message Queues -------key


msqid
owner

used-bytes

perms

status

messages

IPC
ipcrm <msg | sem | shm> IPC_ID

(msg , sem ,
shm ), .

12.4.2.
,
. IPC, .
msgbuf ( /usr/src/linux/include/linux/msg.h) :
struct msgbuf {
long mtype;
char mtext[1];
};

/* */
/* */

: .
, -

142

III.

,
. ,
, .
msgbuf :
struct my_buf {
long mtype;
char mtext[256];
}


, :
struct my_buf {
long mtype;
char mtext[256];
long status;
}

/usr/src/linux/include/linux/msg.h:
#define MSGMAX 4056

sysctl (
kernel.msgmax). , msgmax
, .
long (4 + 4 = 8 ) mtext 256 ,
264 .
msg (. msg.h):
struct msg {
struct msg *msg_next;
long
msg_type;
char *msg_spot;
short msg_ts;
};

, msg_next, . , msg_type, , ,
msg_buf. ,
, msg_ts, .
IPC .
msqid_ds ( /usr/src/linux/include/
linux/msg.h):
struct msqid_ds {
struct ipc_perm msg_perm;
struct msg *msg_first;
struct msg *msg_last;
time_t msg_stime;

12.
time_t
time_t
struct
struct
ushort
ushort
ushort
ushort
ushort

143

msg_rtime;
msg_ctime;
wait_queue *wwait;
wait_queue *rwait;
msg_cbytes;
msg_qnum;
msg_qbytes;
msg_lspid;
msg_lrpid;

};

msg_perm, . ipc_perm ( linux/ipc.h):


struct ipc_perm {
key_t key;
/* */
ushort uid;
/* uid gid */
ushort gid;
ushort cuid;
/* uid gid */
ushort cgid;
ushort mode;
/* */
ushort seq;
/* */
};

seq , , .
IPC MAX, MAX IPC .
msg_perm , . msg_time . msg_rtime , msg_ctime .
wwait rwait , ,
.
msg_cbytes ,
msg_qnum , msg_qbytes
.
: msg_lpid PID , , msg_rpid PID , .

12.4.3.
msgget():
#include <sys/types.h>
#include <sys/ipc.h>

III.

144
#include <sys/msg.h>
int msgget(key_t key, int msgflg);

, ftok(). :
IPC_CREAT , ;
IPC_EXCL IPC_CREAT,

, .
IPC_CREAT ( IPC_EXCL) ,
( ).
IPC_EXCL IPC_CREAT, ,
, , msgget()
1.
IPC_CREAT :
IPC_CREAT | 0660

msgget() 1,
errno:
EACCESS IPC;
EEXIST , , -

;
EIDRM ;
ENOENT ( );
ENOMEM ;
ENOSPC (. . -

).
:
key_t key;
int id;

/* IPC */
/* ID */

/* */
key = ftok ("/etc/passwd", 'd');
/* */
if ((id = msgget ( key, IPC_CREAT | 0660 )) == -1)
{
printf("Error\n");
exit(1);
}

12.

145

12.4.4.
( ) , . . .
msgsend():
int msgsnd(int msqid, struct msgbuf *msgp, size_t msgsz, int msgflg);

, . msgget().
.
(4 ).
0 IPC_NOWAIT, ,
,
. ( 0), , , .
, 0, 1, .
errno :
EAGAIN , IPC_NOWAIT, . . -

;
EACCESS ;
EFAULT msgp (

);
EIDRM ;
EINVAL ;
ENOMEM .

:
/* res
length */
int res, length;
struct my_buf *buf;
/* */
/* */
length = sizeof(struct my_buf);
/* id */
if((res = msgsnd( id, &buf, length, 0)) == -1)
{
printf("Error\n");
exit(1);
}

, , id . .

III.

146

,
( 12.6).
12.6. queue-demo.c
#include
#include
#include
#include

<stdio.h>
<stdlib.h>
<linux/ipc.h>
<linux/msg.h>

main()
{
int id;
key_t key;
int res, length;

/* ID */
/* */
/* */

/* */
struct my_buf {
long
mtype;
/*
int
op_type;
int
l_op;
int
r_op;
} msg;

*/
/* */
/* */
/* */

/* IPC- */
key = ftok(".", 'a');
/* */
if ((id = msgget ( key, IPC_CREAT | 0660 )) == -1)
{
printf(" \n");
exit(1);
}
/* */
msg.mtype
= 1; /* , ! */
msg.op_type = 0; /* */
msg.l_op = 5;
msg.r_op = 4;
/* */
length = sizeof(struct my_buf);
if((res = msgsnd( id, &msg, length, 0)) == -1)
{
printf(" \n");

12.

147

exit(1);
}
return 0;
}

ipcs. . 12.1,
0666.

. 12.1.

, . msgrcv():
size_t msgrcv(int msqid, struct msgbuf *msgp, size_t msgsz, long msgtyp, int
msgflg);

, . , .
. . . IPC_NOWAIT, , ,
ENOMSG.
msqrcv() , ,
1 . errno :
E2BIG , msgsz;
EACCESS ;

III.

148

EFAULT ;
EIDRM ; ,

, ;
EINTR ;
EINVAL ,

;
ENOMSG , . , -

IPC_NOWAIT, .
:
int
id;
int
res, length;
struct my_buf buf;
int type=1;

/* ID */
/* , */
/* */
/* */

length = sizeof(struct my_buf);


if((res = msgrcv( id, &buf, length, type, 0 )) == -1)
{
printf("Error\n");
exit(1);
}

, ,
.
msg_exists(), : id type . TRUE,
FALSE.
int msg_exists(int id, long type )
{
int
res;
if((res = msgrcv( id, NULL, 0, type, IPC_NOWAIT )) == -1)
{
return(TRUE);
}
else
return(FALSE);
}

msgctl(). , msgctl() , :

12.

149

#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/msg.h>
int msgctl(int msqid, int cmd, struct msqid_ds *buf);

ID , , , , IPC_STAT, buf .
IPC_RMID:
msgctl(id, IPC_RMID, NULL);

msgctl() man 2 msgctl.

12.5.
12.5.1.
IPC, , .
, . : 0 ( ) 1 ( ).
, , .
( ). ,
. 1 0, .
, , , ,
. .
, , .
, . ,
- , 100 .
100 , .
1
, 1.

12.5.2.
semid_ds, /usr/src/linux/include/linux/sem.h:
struct semid_ds {
struct ipc_perm sem_perm;
time_t sem_otime;

/* */
/* */

III.

150
time_t
struct
struct
struct
struct
ushort

sem_ctime;
/* */
sem *sem_base;
/* */
wait_queue *eventn;
/* */
wait_queue *eventz;
sem_undo *undo;
/* undo */
sem_nsems;
/* */

};

.
sem:
struct sem
short
ushort
ushort
ushort
};

{
sempid;
semval;
semncnt;
semzcnt;

/* PID */
/* */
/* , . */
/* , . . */

:
sem_pid PID , ;
sem_semval ;
sem_semncnt , ,

. . ;
sem_semzcnt , .

12.5.3.
. semget(),
:
#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/sem.h>
int semget ( key_t key, int nsems, int semflg );

IPC, , , ftok().
, . , IPC_CREAT IPC_EXCL. :
IPC_CREAT | 0660

sem.h:
#define SEMMSL 32 /* <= 512 */

, , .

12.

151

semget() 1 .
errno :
EACCESS ;
EEXISTS , ;
EIDRM ;
ENOENT , IPC_CREAT;
ENOMEM ;
ENOSPC .

semget():
if((sid = semget(key, n, IPC_CREAT|IPC_EXCL|0666)) == -1)
{
printf(" \n");
exit(1);
}

12.5.4.
semop() :
int semop(int semid, struct sembuf *sops, unsigned nsops);

,
semget(). , . .
sembuf:
struct sembuf {
ushort sem_num;
short sem_op;
short sem_flg;
};

/* */
/* */
/* */

sem_num , .
(sem_op) . ,
IPC_NOWAIT. IPC_NOWAIT , "" ,
( ).
, semop(), .
100 . , "" , sembuf :
struct sembuf dev_lock = { 0, -1, IPC_NOWAIT };
semop(sid, &dev_unlock, 1);

III.

152

, "" , ,
sembuf :
struct sembuf dev_unlock = { 0, 1, IPC_NOWAIT };
semop(sid, &dev_unlock, 1);

, , semop() 0. 1, errno :
E2BIG ( nsops)

;
EACCESS ;
EAGAIN (
IPC_NOWAIT),

EFAULT sops ;
EIDRM ;
EINTR ;
EINVAL semid;
ENOMEM Undo-;
ERANGE .

12.5.5.
semctl():
int semctl ( int semid, int semnum, int cmd, union semun arg );

,
( 0). ,
. (union) , .
, . . , . 12.1.
12.1.

IPC_STAT

semid_ds buf semun (. )

IPC_SET

ipc_perm semid_ds

IPC_RMID

GETALL

.
unsigned short,
array

GETNCNT

12.

153
12.1 ()

GETPID

PID , semop()

GETVAL

GETZCNT

SETALL

. array
semun

SETVAL

.
val semun

, . .
semctl():
union semun {
int val;
struct semid_ds *buf;
ushort *array;
struct seminfo *__buf;
void *__pad;
};

/*
/*
/*
/*

SETVAL */
IPC_STAT IPC_SET */
GETALL SETALL */
IPC_INFO */

semctl() , 1. errno :
EACCESS ;
EFAULT arg ;
EIDRM ;
EINVAL semid;
EPERM cmd;
ERANGE .

. id, n. GETVAL (. . 12.1):


int value;
int N;
value=semctl(id, N, GETVAL, 0);

:
int c, val;
for (c = 0; x < 5; c++)

III.

154
{
val=semctl(sid,c,GETVAL,0);
printf(" %d: %d\n",c,val);
}

12.6.
12.6.1.
IPC .
: "" , . ,
, .

shmid_ds, /usr/src/linux/include/linux/shm.h:
struct shmid_ds {
struct ipc_perm shm_perm;
/* */
int
shm_segsz;
/* */
time_t shm_atime;
/* */
time_t shm_dtime;
/* */
time_t shm_ctime;
/* */
unsigned short shm_cpid;
/* PID */
/* PID - */
unsigned short shm_lpid;
short shm_nattch;
/* */
unsigned short shm_npages;
/* ( ) */
/* $frames -> S$*/
unsigned long *shm_pages;
struct vm_area_struct *attaches; /* */
};

,
. shm.h.
shmget(), , . , ( ). . shm_nattach
.

12.6.2.

shmget().
:

12.

155

#include <sys/ipc.h>
#include <sys/shm.h>
int shmget(key_t key, int size, int shmflg);

, , .
, ftok(). , . IPC_CREAT,
, , .
IPC_EXCL IPC_CREAT, . IPC_EXCL .
shmget()
1, . errno :
EACCESS ;
EINVAL ;
EEXISTS , .

, IPC_EXCL IPC_CREAT , ;
IDRM ;
ENOMEM .

:
shid = shmget( key, size, IPC_CREAT | 0660 )

, shmat():
int shmat ( int shmid, char *shmaddr, int shmflg );

, . .
0 : .
. :
SHM_RND (

);
SHM_RDONLY .

shmat() ,
, 1, . errno
:
EACCESS ;
ENOMEM ;
EINVAL , . . ID -

(shmaddr).

III.

156

:
char *ptr;
ptr = shmat(sh_id,0,0);


, .
, , .
shmdt():
int shmdt ( char *shmaddr );

1. errno
: EINVAL, . . .
shmctl():
int shmctl ( int shmid, int cmd, struct shmid_ds *buf );

, , , IPC_STAT/IPC_SET.
:
IPC_STAT shmid_ds buf;
IPC_SET ipc_perm shmid_ds -

. buf;
IPC_RMID , -

. , .
, shmctl() 0 1,
.

12.6.3.
, ,
( 12.7).
12.7. share.c
#include
#include
#include
#include
#include

<stdio.h>
<stdlib.h>
<sys/types.h>
<sys/ipc.h>
<sys/shm.h>

/* 256 */
#define SIZE 256

12.

157

int main(int argc, char *argv[])


{
key_t key;
/* */
int shmid, c;
/* */
char *ptr;
/* */
/* */
key = ftok(".", 'D');
/* */
shmid = shmget(key, SIZE, IPC_CREAT|0660);
/* */
if((ptr = shmat(shmid, 0, 0)) == -1)
{
printf("shmat() error\n");
exit(1);
}
/* ptr */
return 0;
}

ipcs , .
. , :
shm_change_mode(int shmid, char *mode)
{
struct shmid_ds mds;
shmctl(shmid, IPC_STAT, &mds);
printf(" : %o\n", mds.shm_perm.mode);
sscanf(mode, "%o", &mds.shm_perm.mode);
shmctl(shmid, IPC_SET, &mds);
printf(" : %o\n", mds.shm_perm.mode);
}

, :
.

158

III.

13


13.1.
, Linux? ,
. ,
, . ,
.
, Windows . , . ( ,
, )
. , "" "" , .
Linux - .
, , .
, . ,
, Windows, .
, , ,
,
. , , NTFS SCSI-, NTFS SCSI-. ( NTFS,
SCSI), .
, , .
, , , ,
, ? ,
,
"" .
,
. ,

13.

159

SCSI-, SCSI.
ext2, ext3, ext4 ""
Linux.
, ? , ,
. .
.
, SCSI ext3. , NTFS-. insmod
,
. , /etc/modules.conf .
-
, , . . , , , .
- ,
, , . , ,
, (
). .

. ,
, , , .
, ""
.
.
, .

Linux, ,
, .

13.2. lsmod, insmod, modprobe


, .
insmod . ,
, , :
# insmod //.o

160

III.

/etc/modules.conf ( /etc/modules). ,
, insmod .
/etc/modules.conf
/etc/modprobe.conf, , modules.conf. 13.1 /etc/modprobe.conf.
13.1. /etc/modprobe.conf
alias eth0 pcnet32
alias sound-slot-0 snd_ens1371
install scsi_hostadapter /sbin/modprobe mptscsih; /sbin/modprobe mptspi;
/sbin/modprobe ata_piix; /sbin/modprobe ahci; /bin/true
install usb-interface /sbin/modprobe ehci_hcd; /sbin/modprobe uhci_hcd;
/bin/true


:
man modprobe.conf

modprobe, ,
.
(, , , remove).
modprobe . , insmod. insmod
,
"" . modprobe
( ), :
# modprobe ivtv

ivtv. ,
, .
, /etc/modules.conf
/etc/modprobe.conf. . , /etc/modules.conf
( /etc/modules), . , /etc/modprobe.conf, , , . ,
, /etc/modprobe.conf.
( /etc/modprobe.conf)
modprobe . /etc/modprobe.conf , . ,
. , . .
.

13.

161

/etc/modules.conf, /etc/modprobe.preload. , .
/etc/modprobe.conf /etc/modprobe.preload
/etc/modprobe.d /etc/modprobe.preload.d. .
,
.
/etc/modprobe.conf /etc/modprobe.preload. ,
,
/etc/modprobe.d ( /etc/modprobe.preload.d,
).
/etc/sysconfig/modules. ,
, .
, Ubuntu /etc/modprobe.conf, /etc/modules /etc/modprobe.d. ,
, , Linux- .
, ? ,
, - /etc/modprobe.conf,
/etc/modprobe.preload ( ).
/etc/modules.conf /etc/modules
.
.

insmod ,
. lsmod
. root
less
lsmod:
# lsmod | less

rmmod. , , .

13.3.
,
:
make make,

(, , ), ,
, ;

162

III.

kernel-source , kernel-source

;
kernel-headers, linux-userspace-headers ,

,
headers
;
kernel-default-devel , . -

, kerneldevel kernel-*-devel.
, ,
.

13.4.
, . - ,
rmmod.
"" module.h, :
#include <linux/module.h>

kernel.h :
#include <linux/kernel.h>

, /usr/include/linux, /usr/src/linux/include/linux.
init_module(),
.
cleanup_module(). .
. ,
, printk(). printk() , /var/log/messages. , .
, , "" ( 13.2).
13.2. first.c
#include <linux/module.h>
#include <linux/kernel.h>
int init_module(void)

13.

163

{
printk(KERN_ALERT "Hello from kernel!\n");
return 0;
}
void cleanup_module(void)
{
printk(KERN_ALERT "first.c: removed\n");
}

, init_module() 0, , . ,
, . . , .
cleanup_module() .
printk(). ,
(, , syslog, klogd, syslog-ng ).
printk() .
, . klogd syslogd, , , .

KERN_ALERT. , ,
. , ,
.
, .
. 13.1.
13.1.

KERN_DEBUG

KERN_INFO

KERN_NOTICE

KERN_WARNING

: -

KERN_ERR

KERN_CRIT

KERN_ALERT

""

KERN_EMERG

"" ( )

164

III.

KERN_ERR (KERN_CRIT, KERN_ALERT, KERN_EMERG)


, ,
, . , KERN_EMERG
, .
, ,
KERL_ALERT, "" .
2.3.13 init_module() cleanup_module(). . , .
module_init() module_exit(), linux/init.h. 13.3 .
13.3. first2.c
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/init.h>
static int __init first_init(void)
{
printk(KERN_ALERT "Hello from kernel\n");
return 0;
}
static void __exit first_exit(void)
{
printk(KERN_ALERT "first.c: removed\n");
}
module_init(first_init);
module_exit(first_exit);

module.h ,
:
MODULE_LICENSE("GPL");
/* */
MODULE_AUTHOR("Denis Kolisnichenko");
/* */
MODULE_DESCRIPTION("Driver for /dev/mydev"); /* */
MODULE_SUPPORTED_DEVICE("mydev");
/* */

, , .

13.

165

13.5.
,
. , .
, ,
linux/module.h , , ...
, , :
, ,

(. , );
X.Org (X Window).

X.Org? , , printk(), ! , .
printf()
. , printk(),
X.Org /var/log/messages.
Linux 12 ( 1999 ). 2.2 2.4 . , -
(
).
:
gcc -DLINUX -DMODULE -D__KERNEL__ -c _.c

, , ,
linux/module.h . ( -I),
gcc - asm/*.h.
, . kbuild . .
, . first.c /root/module.
Makefile :
obj-m := first.o

, Makefile. . Makefile .
, /root/module, :
# make -C /usr/src/linux SUBDIRS=$PWD modules

, . , -C , Makefile. ,

166

III.

Makefile, Makefile . /usr/src/linux /usr/src/linux-2.6.x.x. ,


, .
make modules ( !)
/usr/src/linux/Makefile ( Makefile ). ,
, (
$PWD make , ). make Makefile
.
. 13.1.
. ,
. make, . . 13.1 ,
. , . 2.6
"" ko o, . /root/module/first.ko.

. 13.1.

. 13.2.

13.

167

.
make , (. 13.2).
, openSUSE 11.2
Mandriva 2010.1 .

. 13.3. ?

. 13.4.

168

III.

. /usr/src/linux
:
make menuconfig

Exit. menuconfig ,
, .
Yes (. 13.3), , (. 13.4).
/root/module make:
# make -C /usr/src/linux SUBDIRS=$PWD modules

13.6.
:
# insmod ./first.ko

: first.ko, first.o.
, .
, :
insmod: error inserting './first.ko": -1 Invalid module format

, , , ! ,
.
, .
, , ,
(, , ,
). . ,
2.6.33.3, , /usr/src/linux /usr/src/linux-2.6.33.3.
, , 2.6.33.5, RPM- .
, 2.6.33.5, . , , . ,
.
. ,
. ,
, kernel.org. -

13.

169

, ,
, .

, , --force-vermagic modprobe, modprobe --forcevermagic first. , ,
.

? , . :
#
#
#
#
#

make
make
make
make
make

menuconfig
dep
modules
modules_install install

,
(
/usr/src/linux-x.x.x.x*).
. .
, ( ) . ,
. ,
( kernel.org) . ,
.
? , ,
,
. .
modinfo (. 13.5):
# modinfo ./first.ko

. 13.5.

. 13.5:
2.6.33.5-desktop, 2.6.33.5-server,
.

170

III.

kernel-source ,
, RPM- , . ,
2.6.33.5-server,
kernel-source "" ""
. 2.6.33.5-desktop.
Mandriva.
. , kernel-server-devel-2.6.33.52mnb , "" .
/usr/src linux-server-2.6.33.5.2mnb, /usr/src/server.
:
# make -C /usr/src/server SUBDIRS=$PWD modules

. 13.6: ,
insmod "". insmod
, ,
/var/log/messages (. 13.7).
/proc/modules. (. 13.8).

. 13.6.

13.

171

. 13.7.

. 13.8. first

172

III.

, , , : !

13.7.
. (
, ):
#include <linux/kernel.h>
#include <linux/module.h>

, (file1.c file2.c).
Makefile :
obj-m += big.o
big-objs := file1.o file2.o

13.8.
13.8.1.
, ( ),
? : ""
. ,
.
, .
, . printf(). libc.
. , . : ,
, .

.
, ,
/proc/kallsyms.
?
, .
"Hello, world". , ,
:
strace hello-world

13.

173

? write()
strace. .
?
. ,
write() ,
"write()". , . . ,
ps,
top .

13.8.2. ,

( ) .
.
.

. , " ",
( ).
.
.
. , , , . . . , , , , .
,
. ,
.
, . , ,
.
. ,

. .
, ,
. . .

174

III.

, .
, , ,
root.

,
, , .
, . : . , Linux , . , - , Linux
. "Understanding the
Linux Kernel" O'Reilly Media. ,
: 10 , ( , , - ), , 2000 2.2, 2.6.

13.8.3.
, :
. , .
, - . ,
, . , .
, .
, , . ,

( , ). ,
.
, . :
ls -l /dev/sda[1-2]

, (, ),
(14).
. 13.9. , :
(8) , (/dev/sda1
/dev/sda2) . .
, .
. , , -

13.

175

. ,
"" , .
, : . ( ), . . 13.9:
( r) b ( . block). ,
, c ( . char), .

. 13.9.

mknod, :
mknod /dev/sda3 b 8 3

(b) /dev/sda3,
8, 3.
/dev , .
Linux .
/dev/sda3, , :
. ,
"",
, "" .

13.9.
13.9.1.
- . file_operations linux/fs.h. , . ,
. , , NULL. :
struct file_operations {
struct module *owner;
loff_t(*llseek) (struct file *, loff_t, int);
ssize_t(*read) (struct file *, char __user *, size_t, loff_t *);
ssize_t(*aio_read) (struct kiocb *, char __user *, size_t, loff_t);
ssize_t(*write) (struct file *,
const char __user *, size_t, loff_t *);

176

III.

ssize_t(*aio_write) (struct kiocb *, const char __user *, size_t,


loff_t);
int (*readdir) (struct file *, void *, filldir_t);
unsigned int (*poll) (struct file *, struct poll_table_struct *);
int (*ioctl) (struct inode *, struct file *, unsigned int,
unsigned long);
int (*mmap) (struct file *, struct vm_area_struct *);
int (*open) (struct inode *, struct file *);
int (*flush) (struct file *);
int (*release) (struct inode *, struct file *);
int (*fsync) (struct file *, struct dentry *, int datasync);
int (*aio_fsync) (struct kiocb *, int datasync);
int (*fasync) (int, struct file *, int);
int (*lock) (struct file *, int, struct file_lock *);
ssize_t(*readv) (struct file *, const struct iovec *, unsigned long,
loff_t *);
ssize_t(*writev) (struct file *, const struct iovec *, unsigned long,
loff_t *);
ssize_t(*sendfile) (struct file *, loff_t *, size_t, read_actor_t,
void __user *);
ssize_t(*sendpage) (struct file *, struct page *, int, size_t,
loff_t *, int);
unsigned long (*get_unmapped_area) (struct file *, unsigned long,
unsigned long, unsigned long,
unsigned long);
};

: . , ,
read, write, open release, file_operations
:
struct file_operations fops = {
.read = mydevice_read,
.write = mydevice_write,
.open = mydevice_open,
.release = mydevice_release
};

fops.
file_operations fops . ,
. fops, , file_operations.
. file_operations.
(. . ) file,
linux/fs.h. file filp.

13.

177

13.9.2.
, , ?
, . . . ,
- .

.
register_chrdev(), linux/fs.h:
int register_chrdev(unsigned int major,
const char *name, struct file_operations *fops);

,
, file_operations.
,
.
, ? . 0

.
Documentation/devices.txt, , , . :
, , 77, , .
: , , ,
( ). mknod()
. cleanup_module() .

13.9.3.
( ) . /var/log/messages. ,
mknod():
,
mknod.
, . : .
13.4.

III.

178
13.4. mydev.c
#include
#include
#include
#include

<linux/kernel.h>
<linux/module.h>
<linux/fs.h>
<asm/uaccess.h>

/* put_user */

/* */
int init_module(void);
void cleanup_module(void);
static int mydevice_open(struct inode *, struct file *);
static int mydevice_release(struct inode *, struct file *);
static ssize_t mydevice_read(struct file *, char *, size_t, loff_t *);
static ssize_t mydevice_write(struct file *, const char *, size_t, loff_t *);
#define SUCCESS 0
#define DEVICE_NAME "mydev"
#define BUF_LEN 128
static
static
static
static

int Major;
int Device_Status = 0;
char msg[BUF_LEN];
char *msg_Ptr;

/* */
/* */
/* */
/* , 1 = */
/* */

/* */
static struct file_operations fops = {
.open = mydevice_open,
.release = mydevice_release,
.read = mydevice_read,
.write = mydevice_write
};

/* */
int init_module(void)
{
/* */
Major = register_chrdev(0, DEVICE_NAME, &fops);
if (Major < 0) {
printk(KERN_ALERT "register_chrdev() error %d\n", Major);
return Major;
}
printk(KERN_NOTICE "Major number %d\n", Major);
printk(KERN_NOTICE "Please create a dev file with\n");
printk(KERN_NOTICE "'mknod /dev/mydev c %d 0'.\n", Major);

13.

179

return SUCCESS;
}
void cleanup_module(void)
{
/* */
int res = unregister_chrdev(Major, DEVICE_NAME);
if (res < 0)
printk(KERN_ALERT "unregister_chrdev() error: %d\n", res);
}
/* */
/* */
static int mydevice_open(struct inode *inode, struct file *file)
{
if (Device_Status)
return -EBUSY;
Device_Open++;
sprintf(msg, "Hello\n");
msg_Ptr = msg;
try_module_get(THIS_MODULE);
return SUCCESS;
}
/* */
static int mydevice_release(struct inode *inode, struct file *file)
{
Device_Status--;
module_put(THIS_MODULE);
return SUCCESS;
}
/* */
static ssize_t
mydevice_write(struct file *filp, const char *buff, size_t len, loff_t * off)
{
printk(KERN_ALERT "Unsupported operation: write()\n");
return -EINVAL;
}
/* ,
.
filp file
buffer ,
lenght
offset */

III.

180

mystatic ssize_t mydevice_read(struct file *filp, char *buffer, size_t length,


loff_t * offset)
{
int bytes_read = 0; /* */

if (*msg_Ptr == 0)

/* ,
0 */

return 0;
/* : .

( ), ,
.
, put_user(),

*/
while (length && *msg_Ptr) {
put_user(*(msg_Ptr++), buffer++);
length--;
bytes_read++;
}
/* */
return bytes_read;
}
MODULE_LICENSE("GPL");
/* */
MODULE_AUTHOR("Denis Kolisnichenko");
/* */
MODULE_DESCRIPTION("Driver for /dev/mydev");
/* */
MODULE_SUPPORTED_DEVICE("mydev");
/* */

? .
:
#include
#include
#include
#include

<linux/kernel.h>
<linux/module.h>
<linux/fs.h>
<asm/uaccess.h>

/* put_user */

.
file_operations(), .
put_user(),
.

13.

181

:
#define SUCCESS 0
#define DEVICE_NAME "mydev"
#define BUF_LEN 128
static
static
static
static

int Major;
int Device_Status = 0;
char msg[BUF_LEN];
char *msg_Ptr;

/* */
/* */
/* */
/* , 1 = */
/* */


0, .
, .
Major .
Device_Status : 1 ( -
), 0 . msg , , /dev/mydev. .
Major. ,
, 0,
register_chrdev(). ,
, mknod. : (
) KER_ALERT (
), KERN_NOTICE (
):
Major = register_chrdev(0, DEVICE_NAME, &fops);
if (Major < 0) {
printk(KERN_ALERT "register_chrdev() error %d\n", Major);
return Major;
}
printk(KERN_NOTICE "Major number %d\n", Major);
printk(KERN_NOTICE "Please create a dev file with\n");
printk(KERN_NOTICE "'mknod /dev/mydev c %d 0'.\n", Major);


(, mknod, /dev, ):
int res = unregister_chrdev(Major, DEVICE_NAME);


, filp:

III.

182
static struct file_operations fops = {
.open = mydevice_open,
.release = mydevice_release,
.read = mydevice_read,
.write = mydevice_write
};

, , :
mydevice_open() , ;
mydevice_release() ;
mydevice_read() , -

;
write() - ,
echo info > /dev/mydev.

: 1, , ,
-EBUSY: . 0, ( )
.
if (Device_Status)
return -EBUSY;
Device_Open++;
sprintf(msg, "Hello\n");
msg_Ptr = msg;

0:
Device_Status--;

. , . . .
,
, bytes_read.
while
put_user(). while bytes_read, :
int bytes_read = 0;
if (*msg_Ptr == 0)

/* */
/* , 0
*/

return 0;
while (length && *msg_Ptr) {
put_user(*(msg_Ptr++), buffer++);

13.

183

length--;
bytes_read++;
}
return bytes_read;

, , . ,
. .
put_user(),
get_user():
static ssize_t
mydevice_write(struct file *file,
const char __user * buffer, size_t length, loff_t * offset)
{
int bwrite;
for (bwrite = 0; bwrite < length && bwrite < BUF_LEN; bwrite ++)
get_user(Message[i], buffer + i);
Message_Ptr = Message;
/* - */
return bwrite;
}

, .
. , , ioctl(), Input/Output ConTroL.
, -
. , 1000, , ,
1000 , . ioctl
:
struct file_operations fops = {
.read = mydevice_read,
.write = mydevice_write,
.ioctl = mydevice_ioctl,
.open = mydevice_open,
.release = mydevice_release,
};

13.10. /proc
/proc
, /proc/modules -

184

III.

. /proc , ,
. /proc/mydev, .
/proc proc_fs.h.
, module.h kernel.h:
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/proc_fs.h>

/proc proc_dir_entry:
struct proc_dir_entry *pde;

proc_dir_entry :
/* */
pde = create_proc_entry("mydev", 0644, NULL);
pde->read_proc = proc_read;
/* */
pde->owner = THIS_MODULE;
/* proc- */
pde->mode = S_IFREG | S_IRUGO;
/* */
pde->uid = 0;
/* UID */
pde->gid = 0;
/* GID */
pde->size = 50;
/* */

proc_read() proc-:
ssize_t
proc_read(char *buffer,
char **buffer_location,
off_t offset, int buffer_length, int *eof, void *data)

:
;

buffer;
;
, ;
eof = 1, ;
, , proc-

.
proc_read :
ssize_t
proc_read(char *buffer,
char **buffer_location,
off_t offset, int buffer_length, int *eof, void *data)

13.

185

{
int length = 0;
static int c = 1;

/* */
/* */

/* , ,
*/
if (offset > 0) {
printk(KERN_INFO "Offset %d, Bytes %d\n", (int)(offset), length);
*eof = 1;
return length;
}
/* */
length = sprintf(buffer,
"This file has been read %d times\n", c);
c++;
return length;
}

pde:
int init_module()
{
int res = 0;
pde = create_proc_entry("mydev", 0644, NULL);
pde->read_proc = proc_read;
pde->owner = THIS_MODULE;
pde->mode = S_IFREG | S_IRUGO;
pde->uid = 0;
pde->gid = 0;
pde->size = 50;
printk(KERN_INFO "Module started. Creating /proc/mydev...");
if (pde == NULL) {
res = -1;
remove_proc_entry("mydev", &proc_root);
printk(KERN_INFO "Error\n");
} else
printk(KERN_INFO "OK\n");
return res;
}

create_proc_entry , proc-
remove_proc_entry() .

III.

186

cleanup_module() :
void cleanup_module()
{
remove_proc_entry("mydev", &proc_root);
printk(KERN_INFO "Module stopped\n");
}

( 13.5).
13.5. procf.c
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/proc_fs.h>
struct proc_dir_entry *pde;
ssize_t
proc_read(char *buffer, char **buffer_location,
off_t offset, int buffer_length, int *eof, void *data)
{
int length = 0;
static int c = 1;

/* */
/* */

/* , ,
*/
if (offset > 0) {
printk(KERN_INFO "Offset %d, Bytes %d\n", (int)(offset), length);
*eof = 1;
return length;
}
/* */
length = sprintf(buffer,
"This file has been read %d times\n", c);
c++;
return length;
}
int init_module()
{
int res = 0;
pde = create_proc_entry("mydev", 0644, NULL);
pde->read_proc = proc_read;
pde->owner = THIS_MODULE;
pde->mode = S_IFREG | S_IRUGO;

13.

187

pde->uid = 0;
pde->gid = 0;
pde->size = 50;
printk(KERN_INFO "Module started. Creating /proc/mydev...");
if (pde == NULL) {
res = -1;
remove_proc_entry("mydev", &proc_root);
printk(KERN_INFO "Error\n");
} else
printk(KERN_INFO "OK\n");
return res;
}
void cleanup_module()
{
remove_proc_entry("mydev", &proc_root);
printk(KERN_INFO "Module stopped\n");
}

( insmod).
/proc mydev. .

13.11. :

. , , , , , - .
.
. (key loggers).
, .
,
, , .

. ,
.
(IRQ) . 1
( Intel). :

III.

188

100
250 . ,
250 , . : 250
1, , , , .
:
#include
#include
#include
#include
#include
#include

<linux/module.h>
<linux/kernel.h>
<linux/workqueue.h>
<linux/sched.h>
<linux/interrupt.h>
<asm/io.h>

myqueue:
#define MY_WORK_QUEUE_NAME "WQsched.c"
static struct workqueue_struct *myqueue;

, , , GPL, , :
MODULE_LICENSE("GPL");

(IRQ 1). , , (
), cleanup_module() :
void cleanup_module()
{
}

:
int init_module()
{
/* */
myqueue = create_workqueue(MY_WORK_QUEUE_NAME);
/* IRQ 1 */
free_irq(1, NULL);
return request_irq(1,
/* IRQ */
keyboard_handler,
/* */
SA_SHIRQ,
"keyboard_irq_handler",
(void *)(keyboard_handler));
}

13.

189

init_module() ,
1 free_irq().
request_irq(). , . SA_SHIRQ , . , /proc/interrupts. ID
. SA_SHIRQ, NULL, - .
keyboard_handler().
-
log_char(), .
log_char() keyboard_handler()
log_char() .
work_struct. log_char() - . , .
irqreturn_t keyboard_handler(int irq, void *dev_id, struct pt_regs *regs)
{
static int initialised = 0;
static unsigned char scancode;
static struct work_struct mytask;
unsigned char status;
/* - */
status = inb(0x64);
scancode = inb(0x60);
/* mytask log_char */
if (initialised == 0) {
INIT_WORK(&mytask, log_char, &scancode);
initialised = 1;
} else {
PREPARE_WORK(&mytask, log_char, &scancode);
}
/* mytask myqueue */
queue_work(myqueue, &mytask);
return IRQ_HANDLED;
}

log_char() . . , ,
=007=. :
cat /var/log/messages | grep =007= | less

III.

190

:
static void log_char(void *scancode)
{
printk(KERN_INFO "=007=: Scancode %x %s.\n",
(int)*((char *)scancode) & 0x7F,
*((char *)scancode) & 0x80 ? "Released" : "Pressed");
}

13.6 .
13.6. sniffer.c
#include
#include
#include
#include
#include
#include

<linux/module.h>
<linux/kernel.h>
<linux/workqueue.h>
<linux/sched.h>
<linux/interrupt.h>
<asm/io.h>

#define MY_WORK_QUEUE_NAME "WQsched.c"


static struct workqueue_struct *myqueue;
MODULE_LICENSE("GPL");
static void log_char(void *scancode)
{
printk(KERN_INFO "=007=: Scancode %x %s.\n",
(int)*((char *)scancode) & 0x7F,
*((char *)scancode) & 0x80 ? "Released" : "Pressed");
}
irqreturn_t keyboard_handler(int irq, void *dev_id, struct pt_regs *regs)
{
static int initialised = 0;
static unsigned char scancode;
static struct work_struct mytask;
unsigned char status;
/* - */
status = inb(0x64);
scancode = inb(0x60);
/* mytask log_char */
if (initialised == 0) {
INIT_WORK(&mytask, log_char, &scancode);

13.

191

initialised = 1;
} else {
PREPARE_WORK(&mytask, log_char, &scancode);
}
/* mytask myqueue */
queue_work(myqueue, &mytask);
return IRQ_HANDLED;
}

int init_module()
{
/* */
myqueue = create_workqueue(MY_WORK_QUEUE_NAME);
/* IRQ 1 */
free_irq(1, NULL);
return request_irq(1,
/* IRQ */
keyboard_handler,
/* */
SA_SHIRQ,
"keyboard_irq_handler",
(void *)(keyboard_handler));
}
void cleanup_module()
{
}

. ,
, . : Linux.

192

III.

IV

Linux
14.

15.

16.

17.

18.

19.

Linux ,
Linux. Linux. , ,
.

14


14.1. Linux
Linux .
, , : ext2, ext3, ext4, XFS, ReiserFS, JFS.
"" (native) Linux ext2 ( ext
Linux),
ext3. ext4.
Linux ext3 ext4.

Linux ext, , .

,
Linux- ext3, ext4, XFS, ReiserFS, JFS.
( ext2) ,
. ,
,
. ,
(, " "). , , , . ,

, , .
ext2 ext3 . , ext3 ext2,
. ext3 (, Total Commander
Ext2Fsd Windows), ext2. , ext4 ext3.

14.

195

ext4 (
ext3).
. ,
, ext3/ext4.
XFS Silicon Graphics 2001 . (
7 /). XFS 512 64 .
, ,
.
(, ),
(, "" ). , , .
, XFS
.
ReiserFS ,
( ). ,
4 , 512 (
), 3,5 .
ReiserFS !
:
. ,
, UPS ( ) .
JFS ( IBM)
AIX, Linux.
(,
XFS). ( 512 4 ). , , , 4 , , .
ext4. , , Linux, "Linux. " (3- ) " Linux (3- )".

14.2. Linux
14.2.1. Linux
Windows Linux , . , Linux ,

IV. Linux

196

. Windows, , Document1.doc Document1, doc . Linux


Document1.doc , .
254 .
( ), / \ ? < > * " |. . , , Windows- ( , ) . (- ,
).
, Linux : FILE.txt FILE.Txt .
/ ( ), \ ( ), Windows.

14.2.2.
Windows , . . , DOS (Disk Operating System) Windows.
Linux . Windows-
: Linux , , . /dev (
devices). , !
DOS, , , , - : PRN (), CON (
, ), LPTn ( , n ), COMn
( ).

- , Linux ""
Microsoft Linux 90- , DOS 80- . . , Microsoft
UNIX, DOS.
,
.

:
/dev/sdx USB-;
/dev/sdxN , N ;
/dev/mouse ;
/dev/modem ( ttySn);
/dev/ttySn , n (ttyS0 -

COM1, ttyS1 COM2 . .).

14.

197


/dev/hdx (. ).

, : .
, , , . .

14.2.3.
, Windows.
( Windows XP).
, ( A:), ( C:, D: E:), CD/DVD (F:).
A:, C:, D: . . Windows
.
Linux . , Linux /dev/sda3.
Linux-.
/, . . ( )
cd /.
, .
, .

, /mnt/cdrom. . 14.4.6, .

14.2.4. Linux
Linux :
/ ;
/bin Linux (cat, cp, ls, login . .);
/boot , Initrd,

;
/dev ;
/etc ;
/home ;
/lib ;
/lost+found

IV. Linux

198

/misc , /opt;
/mnt ;
/proc procfs,

;
/root root;
/sbin , -

root;
/tmp ;
/usr , ,

;
/var , :

, , , . .

14.3.
? ,
. :
,
, .

, ,
: .
,
(ISO 9660).
, ,
. , Linux
open() open(), ,
.
(. 14.1): , .
glibc ( GNU C) . glibc , , ,
: open(), read(), write(), close(), glibc,
.
VFS . . -

14.

199

. VFS, ,
open_ext2() , ext2,
open_vfat() VFAT. , VFS .
.

, PATA
SATA.
ext2/3 ,
. 14.2.
512 .
.
(Master Boot Record,
MBR) , .
.

. 14.1.

. 14.2.

( )
. .
1, 2 4 . . 1.

200

IV. Linux

, . 1 (1024 ).
,
.
/usr/src/linux/include/linux/fs.h:
struct super_block {
struct_head s_list; //
unsigned long s_blocksize;
struct file_system_type *s_type;
struct super_operations *s_op;
struct semaphore
s_lock;
int s_need_sync_fs;
...
}

, i-,
i- ( i- inode, ).
(block map)
. i-, ,
. i- . i- , i- , .
i- .
15 , 12
, . 12 (, 1 = 1 ), .
(13-) ,
, .
, , . ,
1, 2 4 . , 256, 512 1024 .
, ? . 14- , , 15- ,
.
, .
ext3 1 . 2.6
16 , "" 4 . DVD- (
18 ).
, i- , . , . -

14.

201

, i-
(). ( )
,
.
, Linux . ? i- i-
, i-
Linux.

14.4.
14.4.1. mount umount
- ,
. , ,
,
. , .
(, -),
, ,
.
,
/ , . .
, . -
, . ,
, .
(, ) .
( root) :
# mount [] <> < >

,
. , /mnt/cdrom, ,
-, (
/mnt/cdrom).
, /aaa-111. , .

root. root
sudo. , -, :
sudo mount /dev/hdc /mnt/cdrom

IV. Linux

202

mount sudo root.


, mount.
umount:
# umount < >

14.4.2.
. ,
.
, Linux .
.
, /dev/fd0 , /dev/hda (/dev/sda) . /dev.


, -. ,
IDE-, , Fedora 5
/dev/hda, Fedora 8 /dev/sda. , IDE (PATA), /dev/hdx, SCSI/SATA-
/dev/sdx ( x ).
udev
(UUID) ,
(PATA, SATA, SCSI), /dev/sdx, x . udev UUID. ,
IDE- /dev/sda. ,
(. . 14.4.5). ,
SATA- (. . PATA- ,
SCSI ),
IDE (PATA), .

udev , Linux 2.6.
devfs.
/dev.

. /dev/sda. , ,
( ). ,
Windows C:, D: E:. C: (), . Linux 1, C:
/dev/sda1 .
, (D: E:)
/dev/sda2 /dev/sda3. . .

14.

203

(primary partition), (extended partition)


(logical partition).
, .
, 1, 2, 3, 4. D: E: , /dev/sda2 /dev/sda3. , (
11 ). Windows
, ,
. ,
5, . . D: E: , /dev/sda5
/dev/sda6 .
: ,
fdisk.
(/dev/hda), :
# /sbin/fdisk /dev/sda

fdisk.
p <Enter>. (. 14.3).
q <Enter>.

. 14.3.

. 14.3 .
( C:, Windows) .
( 2).

204

IV. Linux

( 5). 3 4 ,
. ,
.


CD- DVD- /dev/srN ( /dev/scdN),
N .
, /dev/sr0 ( /dev/scd0). ,
CD-ROM,
/dev/cdrom. DVD-,
/dev/dvd. :
sudo mount /dev/sr0 /mnt/cdrom
sudo mount /dev/cdrom /mnt/cdrom
sudo mount /dev/dvd /mnt/cdrom

, ,
/mnt/cdrom. , .

. : (/dev/fd0) (/dev/fd1).
:
sudo mount /dev/fd0 /mnt/floppy
sudo mount /dev/fd1 /mnt/floppy

, Windows- /dev/fd0 A:, /dev/fd1 B:.

USB-
USB- ,
(/dev/sd?). , (
/dev/sda) , /dev/sdb. ( , ) :
sudo mount /dev/sdb /mnt/usb

USB- ( ,
) (
, Linux).

14.

205

14.4.3.
, , . :
# mount <> < >

:
# mount /dev/sda5 /mnt/win_d

mount , : -t, -r, -w, -a.


-t .

, .
. :
# mount -t < > <> < >

:
# mount -t iso9660 /dev/hdc /mnt/cdrom

:
ext2 ext3
iso9660
vfat

Linux;

CD-ROM;

FAT, FAT32 ( Windows 9x, ME, XP);

ntfs

NT File System ( Windows NT, XP), NTFS, NTFS-


;
ntfs-3g

ntfs-3g, .
NTFS-.

ntfs-3g, . . ,
www.ntfs-3g.org. , .

-r " ".
-w "/".

,
(, NTFS ,
CD/DVD-).
a ,

/etc/fstab ( , noauto ).
mount -a.

IV. Linux

206

NTFS- ntfs-3g, , , (, Windows ). o force, :


sudo mount -t ntfs-3g /dev/sdb1 /media/usb -o force

14.4.4.
(, Windows-),
/etc/fstab. : (, CD/DVD-, Flash-). , , Mandriva,
/etc/fstab.
Windows- . , ,
fstab:
_ _ _ _

: _ , _ . (1), dump
. (0),
. ,
fsck.
:
;
-

.
.
. 14.1.
14.1. /etc/fstab

auto

.
,

noauto

(
mount -a),
mount

defaults

exec

noexec

14.

207
14.1 ()

ro

" "

rw

"/". ,

user

/ ( root)

nouser

root.

umask

.
Linux' : umask=0

utf8

, UTF-8
. (
KOI8-R) Windows iocharset=koi8-u,codepage=866


/etc/fstab, /etc,
(, gedit, kate), root
( su sudo).

:
/dev/sdc /mnt/cdrom auto umask=0,user,noauto,ro,exec 0 0
/dev/sda1 /mnt/win_c vfat umask=0,utf8 0 0

-,
C:.
. /dev/hdc CD-ROM. -

/mnt/cdrom. , . : iso9660, - ,
auto, . . . . , umask
, - Linux. user ,
. noauto ,
-. ro
" ", exec . , - , , .
. . . ,
( vfat), auto. umask,

208

IV. Linux

, . utf8 .

14.4.5. UUID /etc/fstab


/etc/fstab, UUID
(Universally Unique Identifier), . , Ubuntu, ( fstab) ID, fstab , :
# /dev/sda6
UUID=1f049af9-2bdd-43bf-a16c-ff5859a4116a / ext3 defaults 0 1
# /dev/sda1
UUID=45AE-84D9 /media/hda1 vfat defaults,utf8,umask=007 0 0

SUSE :
/dev/disk/by-id/scsi-SATA_WDC_WD1600JB-00_WD-WCANM7959048-part5 / ext3
acl,user_xattr 1 1
/dev/disk/by-id/scsi-SATA_WDC_WD1600JB-00_WD-WCANM7959048-part7 swap swap
defaults 0 0

, /dev/sda1 ,
1f049af9-2bdd-43bf-a16c-ff5859a4116a.
, !
. , /etc/fstab
, ( , ).
" " :
ls l /dev/disk/by-uuid/

, ,
, ? , Linux
. IDE-.
, (primary),
(secondary), , .

(master), (slave). , ,
, hda (primary
master), hdb (primary slave), hdc (secondary master), hdd (secondary slave). SATA/SCSI- .

.

14.

209

(persistent name). ,
, , , , /dev/hdaN, /dev/hdbN. , Linux , . , ,
. ? .
. . libata. libata PATA hdx, sdx, ( )
. ,
, IDE SATA/SCSI-.
UUID :
UUID=45AE-84D9

/media/sda1

vfat

defaults,utf8,umask=007, gid=46 0 0

UUID ;
/dev/disk/by-id/scsi-SATA_WDC_WD1600JB-00_WD-WCANM7959048-part7
defaults 0 0

swap

swap

/
ext3
defaults
1 1 , ,
.

LABEL=/


by-uuid,
. . UUID, by-id, . . . by-label . :

ls l /dev/disk/by-uuid
ls l /dev/disk/by-id
ls l /dev/disk/by-label
, by-path. sysfs. ,
.

:
ls -lF /dev/disk/by-label

, . 14.2.
14.2.

ext2/ext3/ext4

# e2label /dev/XXX <>

ReiserFS

# reiserfstune -l <> /dev/XXX

JFS

# jfs_tune -L <> /dev/XXX

IV. Linux

210

14.2 ()

XFS

# xfs_admin -L <label> /dev/XXX

FAT/FAT32

Windows

NTFS

# ntfslabel /dev/XXX <>

/etc/fstab . : /dev/disk/by-uuid/*, /dev/disk/by-id/*


/dev/disk/by-label/*, UUID=
LABEL=. , .

14.4.6. mount()
mount(),
umount(). mount() , root.
, mount().
, , mount, ,
mount.c. ,
( do_mount), 14.1. - , 14.1 mount.c BusyBox, UNIX- .
14.1. do_mount
static int
do_mount(char *specialfile, char *dir, char *filesystemtype,
long flags, void *string_flags, int useMtab, int fakeIt,
char *mtab_opts)
{
int status = 0;
char *lofile = NULL;
// , ,
#if defined BB_MTAB
if (fakeIt == FALSE)
#endif
{
#if defined BB_FEATURE_MOUNT_LOOP
if (use_loop==TRUE) {
int loro = flags & MS_RDONLY;
char *lofile = specialfile;

14.

211

specialfile = find_unused_loop_device();
if (specialfile == NULL) {
fprintf(stderr, "Could not find a spare loop
device\n");
return (FALSE);
}
if (set_loop(specialfile, lofile, 0, &loro)) {
fprintf(stderr, "Could not setup loop device\n");
return (FALSE);
}
if (!(flags & MS_RDONLY) && loro) { /* loop is ro, but
wanted rw */
fprintf(stderr, "WARNING: loop device is readonly\n");
flags &= ~MS_RDONLY;
}
}
#endif
// mount()
status = mount(specialfile, dir, filesystemtype, flags,
string_flags);
}

/* , . . status = 0,
, TRUE */
if (status == 0) {
// BB_MTAB,
// mtab
#if defined BB_MTAB
if (useMtab == TRUE) {
write_mtab(specialfile, dir,
filesystemtype, flags, mtab_opts);
}
#endif
return (TRUE);
}
/* mount() */
#if defined BB_FEATURE_MOUNT_LOOP
if (lofile != NULL) {
del_loop(specialfile);
}
#endif
// = EPERM, ,
// root

IV. Linux

212

if (errno == EPERM) {
fatalError("mount: permission denied. Are you root?\n");
}
return (FALSE);
}

mount ( mount.c) .
, . mount() , man. mount() , :
http://www.opennet.ru/man.shtml?topic=mount&category=2&russian=0
! man-
mount(),
.
,
Linux: Linux, , .

15


15.1.
, , .
. 15.1.
15.1.

mkdir <>

cd <>

ls <>

rmdir <>

rm -r <>

:
. , cat ./file, -

file, ;
.. , cd ..,

"" ;
~ ( ).

. :
mkdir directory
cd directory
touch file1.txt

214

IV. Linux

touch file2.txt
ls
cd ..
ls directory
rm directory
rmdir directory
rm -r directory

(mkdir) directory .
(cd) ( ) . touch file1.txt
file2.txt.
ls . cd .. . , Linux "..", ".". , directory, file1.txt file2.txt ./file1.txt ./file2.txt.
: Linux, Windows, (/), (\).
".." "." Linux "~"
. , /home/den.
dir file1.txt.
:
/home/den/dir/file1.txt

:
~/dir/file1.txt

, (~) . directory ,
, ls :
ls directory

rm . : ! rmdir, . , , . . . . , ,
-r rm .
( ),
(. 15.1).
cp mv : (/) -, -.
-r, () .

15.

215

. 15.1.

15.2.
15.2.1.
unistd.h :
int chdir (const char * path);
int fchdir (int fd);

chdir() , chdir() () . fchdir()


( Linux open() ). 1 ( ).

15.2.2. ,
8 FILE. C DIR. ,
.
dirent.h , :
DIR * opendir (const char * name);
int closedir (DIR * dirp);

opendir()
DIR. , . NULL.

IV. Linux

216

0. 1.
fchdir() fopendir(), , , :
DIR * fopendir (int fd);

,
readdir():
struct dirent * readdir (DIR * dirp);

readdir()
dirent. , readdir() ,
. , readdir().
dirent dirent.h :
struct dirent {
ino_t
off_t
unsigned short
unsigned char
char
};

d_ino;
d_off;
d_reclen;
d_type;

/*
/*
/*
/*

inode */
*/
*/
;
*/
d_name[256]; /* */

d_name, / .
, ( 15.1.)
15.1. ( dir.c)
#include <stdio.h>
#include <dirent.h>
int main (void) {
DIR *dir;
struct dirent *ent;
/* */
char directory[255] = "./";
/* */
dir = opendir(directory);
/* */
while ((ent=readdir(dir)) != false) {
printf("%s\n", ent->d_name);
}

15.

217

/* */
closedir(dir);
return 0;
}

. , rewinddir(), ""
:
void rewinddir (DIR * dirp);

15.2.3.
dirent: , d_name. , stat(), fstat() lstat():
int stat (const char * path, struct stat * buf);
int fstat (int fd, struct stat * buf);
int lstat (const char * path, struct stat * buf);

sys/stat.h.
path,
stat, .
,
fd.
stat.
lstat() . , path, , stat , , .
stat:
struct stat {
dev_t st_dev;
ino_t st_ino;
mode_t st_mode;
nlink_t st_nlink;
uid_t st_uid;
gid_t st_gid;
dev_t st_rdev;

/*
/*
/*
/*
/*
/*

, */
*/
*/
- */
UID */
GID */
/*
*/
off_t st_size;
/* */
unsigbed long st_blksize; /* */
unsigned long st_blocks;
/* */
time_t st_atime;
/* */
time_t st_mtime;
/* */
time_t st_ctime;
/* */
}

IV. Linux

218

,
( 15.2).
15.2. fileinfo.c
#include
#include
#include
#include

<stdio.h>
<sys/stat.h>
<sys/types.h>
<time.h>

int main (void)


{
struct stat s;
if (stat("./fileinfo.c", &s) == -1)
{
printf("Error\n");
return 1;
}
printf("Filename: fileinfo.c\n");
printf("UID: %d GID: %d\n", (int) s.st_uid, s.st_gid);
printf("Size: %ld\n", (long int) s.st_size);
printf("Last access time: %s", ctime(&s.st_atime));
printf("Time of last modification: %s", ctime(&s.st_mtime));
return 0;
}

fileinfo.c. , , . ,
, , .
, / .
.
18, ,
.
st_mode stat.
. , ,
18, , .
, . 15.2.
15.2.

true,

S_ISDIR()

S_ISCHR()

15.

219
15.2 ()

true,

S_ISBLK()

S_ISREG()

S_ISFIFO()

FIFO

S_ISLNK()

S_ISSOCK()

:
#include <stdio.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <dirent.h>
#include <stdlib.h>
...
struct stat s;
lstat("./fileinfo.c", &s);
if (S_ISREG(s.st_mode)) printf(" \n");
else if (S_ISDIR(s.st_mode)) printf("\n");
else if (S_ISLNK(s.st_mode)) printf("\n");
...

, , . 15.2.
:
lstat(), S_ISLNK() .

15.2.4.
unistd.h :
int rmdir(const char *pathname);

sys/stat.h :
#include <sys/stat.h>
#include <sys/types.h>
int mkdir(const char *pathname, mode_t mode);

. ,
. .
mkdir() ,
, :
mkdir("directory", 0777);

1 0 .

16


16.1.
Linux
(. 16.1), , .
16.1. Linux,

touch <>

cat <>

tac <>

, . . , . .

cp <1> <2>

<1> <2>. <2> ,


mv <1> <2>

<1> <2>.

rm <>

locate <>

which <>

, ,
. , PATH ( )

less <>


( )

( . 16.1):

16.

221

touch file.txt
echo "some text" > file.txt
cat file.txt
cp file.txt file-copy.txt
cat file-copy.txt
rm file.txt
cat file.txt
mv file-copy.txt file.txt
cat file.txt

. 16.1.

(touch) file.txt.
(echo) some text . > /,
.
(cat) some text. (cp) file.txt filecopy.txt. cat, file-copy.txt , .
(rm) file.txt. ,
. , <Y>,
, <N>. ? : cat
file.txt. , .
(mv) file-copy.txt file.txt. file.txt. , ,
DOS, Windows .

222

IV. Linux

. ,
, tmp.
: rm *tmp.
,
: rm *.
, ?, , , ,
. , ,
s:
rm s??

s14, sqm, sr6 . ., , s.


.
Linux , . . :
.
, .
, .
,
. , Linux-: ,
/home
. ,
, , /home. .
, , .
ln:
ln file.txt link1
ln -s file.txt link2

link1,
file.txt. link2,
file.txt.
( link1 link2), file.txt.
. ,
link2, file.txt , -
, .
link2 ,
. link1,
file.txt, .

16.

223

16.2.
16.2.1. : rename()
stdio.h rename(),
. rename():
int rename (const char * oldpath, const char * newpath);

, .
0, - , 1.
( 16.1).
16.1. rename.c
#include <stdio.h>
int main (int argc, char ** argv)
{
if (argc < 3) {
printf(": rename _ _\n");
return 1;
}
if (rename(argv[1], argv[2]) == -1) {
printf(" \n");
return 2;
}
return 0;
}

, rename(). , rename() ,
stdio.h, .

16.2.2. :
unlink() rmdir()
unlink() unistd.h
:
int unlink (const char * pathname);

,
0 1, .

224

IV. Linux

, . , rmdir(),
15.
unlink():
#include <stdio.h>
#include <unistd.h>
...
if (unlink(fname) == -1) {
printf(" \n");
return 1;
}

16.2.3. umask()
umask() :
mode_t umask (mode_t mask);

, .
. man umask.

16.2.4.
. 16.1 . ,
. link(), symlink():
int link (const char *existing, const char *new);
int symlink (const char *existing, const char *new);

unistd.h, 1 0 .
(existing) , ,
.
, ,
readlink(), unistd.h:
ssize_t readlink(const char *path, char *buf, size_t bufsiz);

, ,
, , . , 1.

16.

225

C '\0', readlink() \0, :


int bytes;
/* C link ,
*/
char buffer 1025;
bytes = readlink("link", buffer, 1024);
buffer[1024] = '\0';
printf("%s", buffer);

17



17.1.
14 , , Linux. mount(),
. ,
/etc/mtab (
, /proc/mounts).
, . /etc/fstab (. 14)
, setmntent(),
mntent.h:
FILE * setmntent (const char * FILENAME, const char * MODE);
struct mntent * getmntent (FILE * FILEP);
int endmntent (FILE * FILEP);

setmntent() ,
.
/etc/mtab. .
, , fopen().
NULL, .
, getmntent(), setmntent()
struct mntent. getmntent() NULL,
/etc/mtab.
mntent :
struct mntent
{
char *mnt_fsname;
char *mnt_dir;

/* */
/* */

17.
char *mnt_type;
char *mnt_opts;
int mnt_freq;
int mnt_passno;

227

/* */
/* */
/* dump */
/* fsck */

};

endmntent() , . /mnt/fstab.
, /etc/mtab. .
, , , statvfs():
int statvfs (const char * PATH, struct statvfs * FS);

, statvfs, .
man statvfs,
f_bsize, f_blocks f_bavail. , .
, .
, (
).
. ,
( 17.1). . 17.1.
17.1. fsinfo.c
#include
#include
#include
#include

<stdio.h>
<mntent.h>
<sys/statvfs.h>
<stdlib.h>

int main(void)
{
FILE * f;
struct mntent * record;
struct statvfs fsinfo;
f = setmntent("/etc/mtab", "r");
if (f==NULL)
{
printf("Error: can't open /etc/mtab");
exit(1);
}

228

IV. Linux

while ((record = getmntent(f)) !=NULL)


{
if (statvfs(record->mnt_dir, &fsinfo) == -1) {
printf("Error");
exit(1);
}
printf("Device: %s\n", record->mnt_fsname);
printf("Mount point: %s\n", record->mnt_dir);
printf("Total blocks: %ld\n", (unsigned long int) fsinfo.f_blocks);
printf("Free blocks: %ld\n", (unsigned long int) fsinfo.f_bfree);
printf("Block size: %ld\n", (unsigned long int) fsinfo.f_bsize);
}
endmntent(f);
return 0;
}

. 17.1. fsinfo

17.

229

17.2. basename() getcwd()


. getcwd(), unistd.h:
char * getcwd (char * BUFFER, size_t SIZE);

getcwd():
#include <unistd.h>
...
char * b = (char*) malloc (1024 * sizeof(char));
...
b = getcwd(b, 1024);
printf(" : %s\n", b);

, ,
, basename(),
strings.h:
char * basename (const char * PATH);

:
printf("%s\n", basename("/home/den/thread.c"));

18



18.1. .
chmod()
. , /, . ? , ,
- . ,
. , .
: (r), (w), (x).
.
(. . ),
(. . ,
) . root
, . , root .
, :
ls -l < />

,
ls -l video.txt
-r--r----- 1 den group 300 Apr 11 11:11 video.txt
-r--r-----

. .
. , d ( directory).
(r--)
. , , .

18.

231

, ,
, w x .
(r--) .
, : , .
(---) . , , .
"Access denied".

ls , ,
, , .

chmod.
: ( , r,
w, x) . , UNIX .
, .
:
rw-r-----


(rw-), .
(r--),
.
, :
rw-

, , 1, , , 1, , 0. 110. 110 ,
6. . 18.1.
18.1.

000

001

010

011

100

101

110

111

232

IV. Linux

, . 100,
. . 4. (---) 000, . . 0.
"-". 640 . , :
chmod 640 <_>

:
644 ,

;
666 ;
777 , . , -

.
. ,
script, , :
chmod +x script

, -x:
chmod -x script


chmod (man chmod). chmod(), C-:
#include <sys/stat.h>
int chmod(const char *path, mode_t mode);

, , mode. :
S_IRUSR ;
S_IWUSER ;
S_IXUSR ;
S_IRGRP ;
S_IWGRP ;
S_IXGRP ;
S_IROTH ;
S_IWOTH ;
S_IXOTH .

OR.
, 640 ( ,

18.

233

, )
file.txt :
chmod ("file.txt", S_IRUSR|S_IWUSR|S_IRGRP);

,
file.txt, root.

18.2. .
chown()
"" - , . . - , chown:
chown

, , , , .
C- chown():
#include <sys/types.h>
#include <unistd.h>
int chown (const char *path, uid_t owner, gid_t group);

,
(UID), (GID).
/etc/passwd (UID), /etc/group (GID), getuid() getgid() ( ) .
-, , ( root).

19


19.1.
Linux . "",
, "", . . .
,
(Virtual File System layer).

,
, . /proc ( proc) , /proc/filesystems. 0,
, ,
, . ,
, . . " ". ,
, . , .

sysfs proc. /etc/fstab
:
sysfs
proc

/sys
/proc

sysfs
proc

defaults
defaults

0 0
0 0

sysfs proc ,
. , , . , ,

19.

235

:
/sysfs /proc. -
, . sysfs proc. ,

.

19.2. sysfs
() sysfs Linux, . sysfs 2.6. /sys.
:
block ,

( ). Flash-,
/sys/devices/ , /sys/block
(
usb-storage);
bus , (,

). devices drivers.
devices , (. . /sys/devices);
class , .

class ( , block, );
devices , -

;
drivers . drivers

, .

19.3. /proc
() /proc , , (,
/proc, . process). ,
/proc, " ". /proc ,
, , , .
, , , .

IV. Linux

236

cat:
cat /proc//<_>

proc :
echo "" > /proc//_

19.3.1.
. 19.1 ( ) proc: .
19.1. proc-

/proc/version

/proc/cmdline

/proc/cpuinfo

/proc/meminfo

( ,
free)

/proc/devices

/proc/filesystems

/proc/mounts

/proc/modules

/proc/swaps

19.3.2. ,
/proc/sys/kernel ,
. , , , (. 19.2).
19.2. /proc/sys/kernel

/proc/sys/kernel/ctrl-alt-del

0, <Ctrl>+<Alt>+<Del>
,
init "" , reboot. 1,
<Ctrl>+<Alt>+<Del> Reset.
, 1

/proc/sys/kernel/domainname

, dkws.org.ua

19.

237
19.2 ()

/proc/sys/kernel/hostname

, den

/proc/sys/kernel/panic

" " , "kernel


panic" . , , ,
. 0 ( ) ,

/proc/sys/kernel/printk


. 6 4 1 7.
, 6 (
, ) .
.
. 9.
,
. ,
, ,
syslog

19.3.3. ,
/proc/sys/net , (. 19.3).
19.3. /proc/sys/net

/proc/sys/net/core/message_burst


(DoS). DoS- ,
,
. ( ), . 50 (5 ). , "" ( 5 ),

/proc/sys/net/core/message_cost

, ,
message_burst

/proc/sys/net/core/netdev_max_backlog

.
300. , ,

/proc/sys/net/core/optmem_max

IV. Linux

238

19.3.4. ,

/proc/sys/vm ,
:
buffermem ( ): , , . : 2 10 60;
kswapd , :
, ;

;
,
. 512 32 8.

19.3.5. ,

/proc/sys/fs , .
:
file-max
( 4096);
inode-max (
4096);
super-max ;

, , super-max,
256, . , ,
, ( ).

super-nr -

. , .

19.3.6.
, " ".
, , ? -

19.

239

, /etc/sysctl.conf (,
, !).
: /proc/sys/ ,
, , , . , /proc/sys/vm/buffermem /etc/sysctl.conf :
vm.buffermem = 2 11 60

/etc/sysctl.conf,
echo "" > .

240

IV. Linux


20.

TCP/IP

21.

22.

Linux. 20 TCP/IP. , ,
, . 21 TCP/IP. ,
, 22.

20

TCP/IP
20.1. OSI
80- . :
. (International
Organization for Standardization, OSI) (Open System Interconnection, OSI).
: OSI, OSI. :
1. .
2. .
3. .
4. .
5. .
6. .
7. .
? ,
, ,
( ). OSI, ,
,
. OSI .
( Ethernet) . ,
,
. , OSI ,
.

20. TCP/IP

243

:
,
. . . ( ). : 1000Base-T
Ethernet, 5- (
) 1000 /;
(
, ) .
: PPP (Point-to-Point Protocol). (, . .) (
). , (frames). , , ,
.
MAC-. MAC- (, ,
).
MAC-.
MAC-;
, . . ,
. , . ,
,
, .
: IP (Internet Protocol). , IP
,
TCP/IP, .
, ( , ,
). ,
. (
) .
( . hop).
. ,
volia.net 6 ( ), . 20.1;
. ,
.
. ,

( ) -

V.

244

.
TCP (Transport Control Protocol);
. . ( , , , ),
.
. (, ),
, . .
;

. 20.1. volia.net

, .
. SSL (Secure Socket Layer);
( ) .

, : HTTP (Hyper Text Transfer Protocol),


FTP (File Transfer Protocol), SMTP (Simple Mail Transfer Protocol) . .

20.2.
"". , . .
TCP/IP (Transmission Control Protocol/Internet
Protocol). ,
TCP/IP. , TCP/IP .
TCP, ,
(, , ), . .
. IP
. ,

20. TCP/IP

245

(IP-), , , IP . (DNS, Domain


Name System).
TCP IP
, :
HTTP (Hyper Text Transfer Protocol) . Web-

HTTP
HTTPS (HTTP Secure);
FTP (File Transfer Protocol) . -

. FTP-
, , , .
FTP-, .
, . ,
, .
FTP- ftp.
FTP-;
SMTP (Simple Mail Transfer Protocol) . (e-mail);
POP (Post Office Protocol) ,
;
IMAP (Internet Message Access Protocol)

, , POP,
. IMAP, ,
, POP. , , .
IMAP , . IMAP ,
POP IMAP .
, , ,
, .
IMAP ( ) .

20.3.
IP-. IP- , ( 32- , , ,
). , , IP- () . () IP- ,
. -

V.

246

IP- , .
MAC- ( MAC-), IP-
.
IP-: 127.0.0.1, 192.168.1.79, 111.33.12.99.
, IP- 32- 8-
. 2 256. , , IP- , IP
4,3 .
, IP IPv6 ( IP, , ,
IPv4).
128- ( 32-),
1012 109. IPv6- , . : 1628:0d48:12a3:19d7:1f35:5a61:17a0:765d.

, IPv6 ( IPng IP Next Generation) , .
IPv4, , ,
IPv6 . IPv6 : http://ru.wikipedia.org/wiki/IPv6.

IP- (NIC, Network


Information Center). IP- ,
. , , .
IP-, . ()
"" . IP- 192.168.1.1. IP-
.
, "" IP- () .
( IP-) "" ,
(NAT, Network Address Translation). , -, IP- , IP-. -
,
"", -. , . . , , .
, , IP- NIC? -

20. TCP/IP

247

. IP- , . , , IP- 192.168.1.0.


0 .
:
A , 16 777 216 ,

IP- 1.0.0.0126.0.0.0;
B , 65 536 .
128.0.0.0 191.255.0.0;
, 256 .

D , E ,
( IPv6), D ( ).
. -.
NIC IP- . ,
1000 . , . , B. ,
, 65 536 ,
B, . . ,
, . A, B C . 20.1.
20.1. A, B C

255.0.0.0

255.255.0.0

255.255.255.0

255.255.255.0 256 ( IP-


0 255). , 192.168.1.0, 255.255.255.0,
IP- 192.168.1.0 192.158.1.255.
(192.168.1.0) IP- , . , 254
192.168.1.1 192.168.1.254.
32 : 255.255.255.224
(255 224 = 31 + "" IP-, 32).
, IP- , 192.168.1.0.
, ?
. 192 : 11000000. .
110, C. -

V.

248

10.0.0.0. 10,
: 00001010. 0,
A. . 20.2.
20.2.

10

110

1110

11110

.
255.255.255.255 .
, ,
. , , , : 192.168.5.255. , 192.168.5.0.
127.0.0.1. . , , . . , . . ,
127.0.0.0.
IP-, 127.
IP- ,
. :
192.168.0.0192.168.255.0

( 256 , 255.255.255.0);
172.16.0.0172.31.0.0 B ( 16 , 255.255.0.0);
10.0.0.0 ( , 255.0.0.0).

IP-
, . . 192.168.0.0192.168.255.0.
,
, 10.0.0.0,
. .
10.0.0.0.
, .

21

21.1.

. .
, . open() .
, , (, ).
, ,
. . . , c Linux , , . , write() , read()
. , , ,
Linux , .
,
:
1. socket().
2. bind().
3. (
accept(), connect()).
4. .
5. shutdown() close().
, , socket.h:
#include <sys/socket.h>

V.

250

21.2.
.
socket(), socket.h.
sys/types.h:
#include <sys/types.h>
#include <sys/socket.h>
int socket(int domain, int type, int protocol);


POSIX.1.2001 sys/types.h
Linux. ,
UNIX (, BSD), sys/types.h.

socket() . .
, AF_INET,
TCP/IP.
:
SOCK_STREAM . TCP/IP;
SOCK_DGRAM . UDP;
SOCK_RAW , ( ,

, ).
, 0,
.
SOCK_STREAM, TCP,
SOCK_DGRAM, UDP.

, SOCK_RAW , .
netinet/in.h. SOCK_RAW socket()
/etc/protocols.

socket()
1, .
, bind():
int bind(int sockfd, const struct sockaddr *addr, socklen_t addrlen);

,
sockaddr, ,
, sockaddr
.

21. :

251

sockaddr socket.h (/usr/incude/sys/socket.h):


# define __SOCKADDR_ALLTYPES \
__SOCKADDR_ONETYPE (sockaddr) \
__SOCKADDR_ONETYPE (sockaddr_at) \
__SOCKADDR_ONETYPE (sockaddr_ax25) \
__SOCKADDR_ONETYPE (sockaddr_dl) \
__SOCKADDR_ONETYPE (sockaddr_eon) \
__SOCKADDR_ONETYPE (sockaddr_in) \
__SOCKADDR_ONETYPE (sockaddr_in6) \
__SOCKADDR_ONETYPE (sockaddr_inarp) \
__SOCKADDR_ONETYPE (sockaddr_ipx) \
__SOCKADDR_ONETYPE (sockaddr_iso) \
__SOCKADDR_ONETYPE (sockaddr_ns) \
__SOCKADDR_ONETYPE (sockaddr_un) \
__SOCKADDR_ONETYPE (sockaddr_x25)

sockadd_in, TCP/IPv4, TCP/IPv6 sockadd_in6. ( netinet/in.h) :


struct sockaddr_in
{
__SOCKADDR_COMMON (sin_);
in_port_t sin_port;
/* */
struct in_addr sin_addr; /* IP- */
unsigned char sin_zero[sizeof (struct sockaddr) __SOCKADDR_COMMON_SIZE sizeof (in_port_t) sizeof (struct in_addr)];
};
/* IPv6. */
struct sockaddr_in6
{
__SOCKADDR_COMMON (sin6_);
in_port_t sin6_port;
uint32_t sin6_flowinfo;
struct in6_addr sin6_addr;
uint32_t sin6_scope_id;
};

/* */
/* IPv6 */
/* IPv6 */
/* IPv6- */

IPv6
IPv6, . IPv4 .
sockaddr_in:
sin_ , TCP/IP

AF_INET;

252

V.

sin_port ;
sin_addr , IP-;
sin_zero .

struct in_addr, ,
netinet/in.h:
struct in_addr
{
in_addr_t s_addr;
};

s_addr INADDR_ANY. bind()


. . , : IP- , ,
.
bind() 0 1, . :
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <stdlib.h>
...
int sock;
sock = socket (AF_INET, SOCK_STREAM, 0);
if (sock==-1) {
printf(" \n");
exit(1);
}
struct sockaddr_in client;
...
client.sin_family = AF_INET;
client.sin_addr.s_addr = INADDR_ANY;
client.sin_port = 1235;
bind (sock, (struct sockaddr *)&client, sizeof(client));

21.3.

, . connect(),

21. :

253

listen() accept(). ,
.
listen():
#include <sys/socket.h>
int listen(int sockfd, int backlog);

, ( ).
0.
,
accept().
:
int accept(int sockfd, struct sockaddr *addr, socklen_t *addrlen);

, ,
. accept() . , .
accept() listen()
, :
//
sock2 = accept (sock1, (struct sockaddr *)&client, &ans_len);
//
write (sock2, MSG_TO_SEND, sizeof(MSG_TO_SEND));

accept() .
0, , ,
IP- .
connect(), :
int connect(int sockfd, const struct sockaddr *serv_addr,
socklen_t addrlen);

, , ( ), ,
.
, 0, 1. connect:
struct sockaddr_in server;
struct hostent *h;
...
/* IP- */
h = gethostbyname ("server.ru");

254

V.

memcpy ((char *)&server.sin_addr,h->h_addr,h->h_length);


/* */
server.sin_port = 3333;
/* */
server.sin_family = AF_INET;
/* */
connect (sock, (struct sockaddr *)&server, sizeof(server));

: IP- , gethostbyname(), .
getsockname():
int getsockname(int s, struct sockaddr *name, socklen_t *namelen);

, , ,
.

21.4.
.
. read() write(),
.
send() recv(), .
( UDP), sendto() recvfrom(). , . sendto() , recvfrom()
, .
send() recv():
ssize_t send(int s, const void *buf, size_t len, int flags);
ssize_t recv(int s, void *buf, size_t len, int flags);

, .
.
. send() ,
recv() buf .
, .
/ .
:
man 2 send
man recv

/ 1
.

21. :

255

: send()
(, -),
, . recv() : ,
, . , MSG_DONTWAIT.
.
sendto() recvfrom() :
ssize_t sendto(int s, const void *buf, size_t len, int flags,
const struct sockaddr *to, socklen_t tolen);
ssize_t recvfrom(int s, void *buf, size_t len, int flags,
struct sockaddr *from, socklen_t *fromlen);

send() recv(), -
. ,
sockaddr, ,
( sendto) (
recvfrom).
sockaddr.

21.5.
close(), , , .
shutdown(), close():
int shutdown(int s, int how);

shutdown() , . , , (, ), :
SHUT_RD , ,

.
;
SHUT_WR ;
SHUT_RDWR : , -

.
, , 0 1 . .

22

22.1. /
22.1.1. -
. -, .
,
. , ,
.
, ( ) ,
, . . -
, ,
( , ).
- 22.1.
22.1 , ,
, .
22.1. server.c
#include
#include
#include
#include
#include
#include
#include

<sys/types.h>
<sys/socket.h>
<netinet/in.h>
<netdb.h>
<memory.h>
<stdio.h>
<stdlib.h>

22. :
/* , */
#define PORT 3333
/* */
#define BUF_SIZE 64
/* , */
#define MSG_TO_SEND "My Simple Server v0.0.1\n"
int main () {
/* */
int server_socket, client_socket;
/* */
int answer_len, count=0;
/* */
char buffer[BUF_SIZE];
/* sockaddr_in (sin) */
struct sockaddr_in sin, client;
/* */
server_socket = socket (AF_INET, SOCK_STREAM, 0);
/* , . man memset
*/
memset ((char *)&sin, '\0', sizeof(sin));
/* sin */
sin.sin_family = AF_INET;
sin.sin_addr.s_addr = INADDR_ANY;
sin.sin_port = PORT;
/* 3333 */
bind (server_socket, (struct sockaddr *)&sin, sizeof(sin));
/* */
printf("Server started.\n");
/* */
listen (server_socket, 3);
/* ,
, <Ctrl>+<C> */
while (1) {
/* */
answer_len = sizeof(client);
/* */
client_socket = accept (server_socket,
(struct sockaddr *) &client, &answer_len);

257

V.

258

/* */
write (client_socket, MSG_TO_SEND, sizeof(MSG_TO_SEND));
/* */
count++;
/* ,
anser_len - */
answer_len = read (client_socket, buffer, BUF_SIZE);
/* */
write (1, buffer, answer_len);
/* */
printf("Client no %d\n",count);
/* */
shutdown (client_socket, 0);
/* */
close (client_socket);
};
return 0;
}

, -
. , , . , :
fprintf(stdout, "Client connected: %s\n", inet_ntoa(client.sin_addr));

,
accept():
if (server_socket = socket (AF_INET, SOCK_STREAM, 0) < 0) {
printf("Failed to create socket");
exit(1);
}
...
if (bind (server_socket, (struct sockaddr *)&sin, sizeof(sin)) <0) {
printf("Failed to bind the server socket");
exit(1);
}
...
/* accept */
if (client_socket < 0)
{
printf("Failed to accept client connection");
exit(1);
}

, ,
-.

22. :

259

22.1.2. -
- 22.2. , , , MSG, .
, - ,
. ,
scanf() .
22.2. client.c
#include
#include
#include
#include
#include
#include
#include

<sys/types.h>
<sys/socket.h>
<netinet/in.h>
<netdb.h>
<memory.h>
<stdio.h>
<stdlib.h>

/* ( , IP-),
, */
#define SERVER_HOST "localhost"
#define SERVER_PORT 3333
#define CLIENT_PORT 3334
/* , */
#define MSG "Denis\n"
main () {
int sock;
int answer_len;
int BUF_SIZE = 64;

/* */
/* */
/* */

char buffer[BUF_SIZE];
/* */
/* IP- */
struct hostent *h;
/* */
struct sockaddr_in client, server;
/* */
sock = socket (AF_INET, SOCK_STREAM, 0);
/* client */
memset ((char *)&client, '\0', sizeof(client));
/* */
client.sin_family = AF_INET;

260

V.

client.sin_addr.s_addr = INADDR_ANY;
client.sin_port = CLIENT_PORT;
/* */
bind (sock, (struct sockaddr *)&client, sizeof(client));
memset ((char *)&client, '\0', sizeof(server));
/* IP- */
h = gethostbyname (SERVER_HOST);
/* */
server.sin_family = AF_INET;
/* */
memcpy ((char *)&server.sin_addr,h->h_addr,h->h_length);
/* */
server.sin_port = SERVER_PORT;
/* */
connect (sock, (struct sockaddr *) &server, sizeof(server));
/* */
answer_len = recv (sock, buffer, BUF_SIZE, 0);
/* */
write (1, buffer, answer_len);
/* */
send (sock, MSG, sizeof(MSG), 0);
/* */
shutdown (sock, 0);
close (sock);
exit (0);
}

. 22.1 . -. , ,
. , "Denis" ( ).
,
. ,
, .
.

22.2.
, . / Linux . .

22. :

261

. 22.1.

:
getsockopt() ;
setsockopt() .

:
int getsockopt (int sd, int level,
int option_name,
void *restrict option_value,
socklen_t *restrict option_len);
int setsockopt (int sd, int level,
int option_name,
const void *option_value,
socklen_t option_len);

. , SOL_SOCKET .
( int),
( get*) ( set*).
getsockopt() , , , -

V.

262

(option_value),
option_len. setsockopt() ,
,
option_value, , getsockopt(),
.
. TCP/IP, , . 22.1.
22.1.

SO_DEBUG

(1) / (0)

SO_BROADCAST

(1) / (0)

SO_REUSEADDR

(1) / (0)

SO_KEEPALIVE

SO_KEEPALIVE = 1, TCP
"keepalive probe" .
,

SO_SNDBUF

SO_RCVBUF

SO_SNDTIMEO

- .
- 0. struct timeval

SO_RCVTIMEO

- .
- 0, . . .
struct timeval

TCP_NODELAY

( 1) , . . . 0

TCP_MAXSEG

TCP_NOPUSH

(1)

TCP_NOOPT

TCP (1).
0

setsockopt() 0 , 1, errno :
EBADF ;
ENOTSOCK , ;
EFAULT , optval.

getsockopt() .
getsockopt() :

22. :

263

SO_ERROR (

);
SO_TYPE .

:
int sock;
int optval;
int optlen;
int new_buffsize = 8192;

/* */
/* */
/* optval */
/* */

/* */
sock = socket(AF_INET, SOCK_STREAM, 0);
/* */
optlen = sizeof(optval);
getsockopt(sock, SOL_SOCKET, SO_SNDBUF, &optval, &optlen);
printf("Old value of SO_SNDBUF: %d\n", optval);
/* */
setsockopt(sock, SOL_SOCKET, SO_SNDBUF,
&new_buffsize, sizeof(new_buffsize));
/* */
getsockopt(sock, SOL_SOCKET, SO_SNDBUF, &optval, &optlen);
printf("New value of SO_SNDBUF %d\n", optval);

22.3. ,

. , 10,
, .
SIGIO, SIGURG, SIGPIPE:
SIGIO /, , ;
SIGURG , - ( -

- );
SIGPIPE , .

:
#include <signal.h>
...
/* SIGPIPE */
/* */
sig_handler()

V.

264
{
printf(" SIGPIPE \n");
}
main()
{
int sock;

/* */

/* SIGPIPE */
signal(SIGPIPE, sig_handler);
/* */
}

22.4.
,
.
accept(), connect(), read(), write().
, , , .

ioctl():
ioctl(socket, FIONBIO, 1);

accept(), connect() /
(read(), write(), recv(), recvfrom() .) . accept()
EWOULDBLOCK, connect() , EINPROGRESS.
, ,
: read()
, , , .
.

VI


TCL/Tk
23.

TCL/Tk

24.

TCL

25.

26.

27.

28.

29.

TCL Tk,
TCL . C, TCL/Tk.

23

TCL/Tk
23.1. TCL
TCL (Tool Command Language) . TCL
TK (Took Kit)
.
, . . . dialog . dialog .
TCL, Tk, . GTK,
C. ? ,
C + GTK, , , . , TCL/Tk
. , TCL/Tk: ,
, , . , TCL, , (CAD/CAM),

. , TCL . Tk
,
TCL-.

23.2. TCL/Tk
TCL/Tk Linux ( ) -

23. TCL/Tk

267

. , TCL/Tk.
, tcl tk . , . , Ubuntu
:
sudo apt-get install tcl tk

(yum, zypper
. .).

23.3.
TCL , , , TCL .
, tclsh:
which tclsh

tclsh /usr/bin.
wish, TCL-.
Tk.
,
Exit. , "Hello,
world!", . , . , . . ,
TCL, . , 23.1 TCL/Tk-.
23.1. TCL/Tk-
#!/usr/bin/wish
label .l -width [string length "My First Tk-application"] -text "My First Tkapplication";
button .b -text "Exit" -command exit;
pack .l -padx 40 -pady 10
pack .b -padx 40 -pady 10

Tk.
"My First Tk-application".
.
, :
label .l -width 23 -text "My First Tk-application";

, , . ,
.

268

VI. TCL/Tk

Exit, ( -command) exit.


pack ( ) . -padx -pady,
, 27.
first.tcl :
chmod +x first.tcl
./first.tcl

first.tcl , . , . 23.1.

. 23.1.

TCL,
26,
,
TCL .
TCL- tclsh:
tclsh < TCL->

23. TCL/Tk

269

, TCL,
TCL-, tclsh :
tclsh

TCL-:
%

<Enter>,
. ,
puts (
printf() C).

24

TCL
24.1. TCL
24.1.1. TCL-
TCL- ,
.
. C, Java PHP . ,
, :
, Web- . .
,
, , .
, - .
TCL- ,
(\n) . :
_ 1 ... N

( 23.1) . , first.tcl , ,
.
, ,
,
. , . first.tcl
, .
, .
#.
, , :
#
pust "Hello, world!"; # , !

24. TCL

271

TCL- , . 24.1, .
24.1.

[]

""

{}

24.1.2. puts format:



TCL, puts, ,
. , puts printf() C. puts , format.
puts , ( ) stdout:
puts "Hello, world!";

stdout :
puts stdout "Hello!";

-nonewline (/n) :
puts -nonewline stdout "Hello!";

puts . 25, my.log:


set chan [open my.log a]
set timestamp [clock format [clock seconds]]
puts $chan "$timestamp Message"
close $chan

chan
a ( append) my.log, timestamp , ( puts) " Message". .

272

VI. TCL/Tk

format sprintf() C.
format :
format _ 1 ... N

sprintf(),
. C ( ,
), :
http://www.tcl.tk/man/tcl/TclCmd/format.htm
:
set fmt " %s, %d"
puts [format $fmt "Hello" 123456]

fmt , %s %d. puts , format. format


.
, \n, \t, \a (
) ., C.

24.1.3.
. 23.1 ,
. , :
set val1 "Value 1";
set val2 "Value 2";
set val3 "Value 3";

puts:
puts "$val1 $val2 $val3";
puts {$val1 $val2 $val3};

:
Value 1 Value 2 Value 3

:
val1 val2 val3

, ,
.

24.1.4.
,
set. (=),
.

24. TCL

273

set :
set _

. set:
set
set
set
set

a 123456
s1 String1
s2 "String 2"
s3 {String 3}

a 123 456. ,
, .
, .
.
: . .
. :
set s1 String1;
set s2 {String2};

s2 String2 . s1 : String1;, String1.


tclsh, . :
, , ,
. , TCL,
( ), , TCL-.
- . expr , :
set a [expr 2 + 2];

$ :
set b [expr $a + 2];

a 4 (2 + 2), b 6 (4 + 2).
$, :
puts \$msg;

0 100:
set min 1
set max 100
set random [expr {round($min + (rand() * ($max $min)))}]
puts " : $random"

274

VI. TCL/Tk

24.1.5.
. TCL . :
proc _ { _ } {
... ...
}

: , .
proc dbl {arg} {
set result [expr $arg * 2];
return result;
}

,
:
proc mysum {arg1 arg2} {
set result [expr $arg1 + $arg2];
return result;
}

:
set a [expr dbl(3)];
set b [expr mysum(2,5)];

24.1.6.
gets , ,
.
. gets :
gets -

gets , (EOL).
, <Enter> . , (EOF), 25.
:
puts -nonewline " -: "
flush stdout
set count [gets stdin user_input]
puts " : $user_input"
puts " $count "

.
, ,
, .

24. TCL

275

gets (stdin) user_input


. count. user_input
count.

24.1.7.
expr.
:
expr 1 2 ...

, , :
expr 2 + 3

expr : 2, +
3. .
. 24.2 . , .
. 24.2 .
24.2. TCL

NOT

NOT

<<

>>

<

>

<=

>=

==

!=

eq

VI. TCL/Tk

276

24.2 ()

ne

AND


OR

10

OR

11

&&

AND

12

||

OR

13

x ? y : z

If .. then .. else

,
. , == != , .
eq ne.

24.1.8. if
. TCL , ,
if.
if :
if { _ } {

, . :
if {$a < 0} {
set a 0
}

:
if {1} ?then? {
1
} elseif {2} ?then? {
2
} elseif
...
else {
N
}

24. TCL

277

then ,
C.

24.1.9. while
while while:
while {} {_}

, .
while , if, , (
) :
while { $a < 10 } {
puts $a
incr a
}

, , a 10.
a 1
incr.

24.1.10. for
for :
for {start} {test} {next} {body}

for for . start,


. test, ,
, body. , next, . next
.
:
for {set i 1} {$i < 10} {incr i} {
puts $i;
}

TCL,
"" .

24.2.
24.2.1. string
, .

VI. TCL/Tk

278
string,

:
string 1 [2 3 ...]

string . . ,
compare, ,
. compare ,
. . 24.3 string.
24.3. string

bytelength

compare

( )

equal

1, , 0,

first

index

is

last

length

map

match

, ,

range

, start end

repeat

replace

tolower

toupper

totitle

trim

trimleft

trimright

24. TCL

279

24.2.2.
eq, ne
if, compare, equal string:
set s1 = "string";
set s2 = "string";
if {$s1 eq $s2} {
puts { s1 s2 };
} else {
puts { s1 s2 };
}

compare:
string compare [-nocase] [-length N] strng1 string2

, string1 string2. . , -nocase.


N -length N.
compare , - strcmp(),
:
1 string1 string2;
1 string1 string2;
0 .

compare:
puts -nonewline " : ";
flush stdout;
get stdin str;
if{![string compare $str "admin"]}{
puts " admin";
} else {
puts " $str";
}

equal (
compare). , equal
1 (true), , 0,
. equal,
, , compare.
,
equal:
puts -nonewline " : ";
flush stdout;
get stdin str;

280

VI. TCL/Tk

if{[string equal $str "admin"]}{


puts " admin";
} else {
puts " $str";
}

match 1, . match :
string match [-nocase]

-nocase . * ?. , .
if{[string match "*.jpg" $filename]}{
puts "JPEG-";
} else {
puts " ";
}

* ? :
if {[string match {[A-Z]} $filename]} {
# 1
} else {
# 2
}

24.2.3.
,
. ,
, . .
length bytelength:
string length
string bytelength

.
, .
, , TCL Unicode,
.
:
set str "";
puts " [string length $str] ";
puts " [string bytelength $str] ";

index , N:
string index N

24. TCL

281

0. "",
N "", 1 "" . .
first last :
string first [start]
string last [end]

first . last, , . start


end ,
. 0.
first last:
set str "1234 ## 5678 ## 999";
set start [string first "##" $str];
set end [string last "##" $str];
puts "start = $start";
# 5
puts "end = $end";
# 13

range , start end:


string range start end

, range , replace, .
replace :
string replace start end [_]

replace , start end.


newstr,
_. :
set s "";
set new_s [string replace $s 0 5 "Hello"];
puts $new_s; # Hello

. is ,
, , . . :
string is [-strict]

1, , ,
0 . ("") , -strict (
). ( ) . 24.4.
:
if {[string is integer "123"]} { puts "Interger!" }

282

VI. TCL/Tk
24.4.

alnum

(Unicode)

alpha

ascii

7- ASCII

boolean

control

( Unicode)

digit

(Unicode)

double

,
( , )

false

, FALSE

graph

(Unicode),

integer

lower

,
(Unicode)

print

(Unicode),

space

(Unicode)

true

, TRUE

upper

,
(Unicode)

wordchar

(Unicode) ,

xdigit

24.2.4.
, , . repeat, N :
string repeat N

:
puts [string repeat "X" 10]

X .
, . 24.3.
:
string toupper [start] [end]
string tolower [start] [end]
string totitle [start] [end]

24. TCL

283

start end , ( start = 0, end = _ 1).


trimleft, trimright trim (. . 24.3) ""
:
string trimleft [chars]
string trimright [chars]
string trim [chars]

chars ,
. (, , , ).

24.2.5.
, .
set:
set str1 ", world";
set str2 "Hello $str1";
puts $str2;

, .
append:
append 1 [... N]

append , , ( ):
append $s "Hello " "world " "again";
puts $s;

24.3.
24.3.1. list:
, . list:
list 1 ... N

list set:
set cars [list VAZ GAZ ZAZ]

cars VAZ, GAZ ZAZ.


:
set cars [list "VAZ" "GAZ" "ZAZ"]

284

VI. TCL/Tk

( )
, :
set cars [list "VAZ" "GAZ" "ZAZ" "Alfa Romeo"]

24.3.2. concat:
concat .
, concat. :
set cars1 [list "VAZ" "GAZ" "ZAZ" "Alfa Romeo"];
set cars2 [list "Mazda" "Toyota" "Nissan"];
set allcars [concat $cars1 $cars2];

allcars :
"VAZ" "GAZ" "ZAZ" "Alfa Romeo" "Mazda" "Toyota" "Nissan"

24.3.3. lappend:

- ,
lappend:
lappend cars1 "VW"

24.3.4.
lindex :
lindex [N]

-, .
, . ,
( 0):
for {set i 0} {$i < 3} {incr i} {
puts [lindex $cars $i];
}

, , . llength:
for {set i 0} {$i < [llength $cars]} {incr i} {
puts [lindex $cars $i];
}

lrange:
lrange start end

, start end.

24. TCL

285

24.3.5.
append . linsert
:
linsert 1 [2 ... N]

, ( ).
. linsert , . 0,
. ,
.

24.3.6.

lreplace:
lreplace start end [...]

, start end ( ),
end. end , start end
.
start 0, , start = 0. end , start,
. ,
.

24.3.7.
, ,
lsearch:
lsearch []

. , .
, 1.
.
- , -regexp, lsearch, :
lsearch -regexp

-start N, , . , ,
.

286

VI. TCL/Tk

:
1. , , .
2. -start N+1, N
.
3.
-start N+1, N . .,
.
:
set cars [list "GAZ-21" "VAZ" "GAZ" "ZAZ" "GAZ-24"];
set n 0;
set first 0;
while { $n>-1} {
if { $first > 0 } {
set n [lsearch -start $n+1 $cars "GAZ*"];
} else {
set n [lsearch -start $n $cars "GAZ*"];
if { $n > -1 } incr first;
}
if { $n > -1 } { puts "Find $n"; }
}

, "GAZ*":
Find 0
Find 2
Find 4

. n
. first ,
. , :
set n [lsearch -start $n $cars "GAZ*"];

n 0. , :
set n [lsearch -start $n+1 $cars "GAZ*"];

start n (. . ), ,
.
first = 0, .
, first.
lsearch 1: . Find 1, n: , n > 1.

24. TCL

287

,
0- "" .
:
set cars [list
set n 0;
while { $n>-1}
set n [lsearch
if { $n > -1 }
}

"VAZ" "GAZ" "ZAZ" "GAZ-24"];


{
-start $n+1 $cars "GAZ*"];
{ puts "Find $n"; }

, . VAZ GAZ
, 1 3, 0,
n + 1 (0 + 1).

24.3.8.
lsort:
lsort []


(. 24.5).
24.5. lsort

-ascii

Unicode-

-dictionary

-integer

-real

-command

TCL- (
)

-increasing

-decreasing

-index

-unique

24.3.9.
TCL , . . . split:
split []

VI. TCL/Tk

288

,
, .
, (, CSV )
.
:
set words [split $sentence]

$sentence words.
, . . , join:
join []

, ,
, :
set $sentence2 [join $words]

24.3.10. foreach
"" for
while, foreach.
PHP, for.
foreach "" , , .
foreach:
foreach { }

: , , , ;
, .
for:
for {set i 0} {$i < [llength $cars]} {incr i} {
puts [lindex $cars $i];
}

, foreach:
foreach item $cars {
puts $item;
}

, foreach for.

break.
TCL: break, . continue,
.

24. TCL

289

24.4.
24.4.1.
, . . , , ,
. ,
.
: admin guest. password, :
set passwords(admin) "qwerty";
set passwords(guest) "123";

:
puts $passwords(admin);

24.4.2. array:
string, array,
(. 24.6). array .
24.6. array

array anymore _

1,
array nextelement, 0

array nextelement
_

.
,

array startsearch


,
anymore nextelement

array donesearch
_

,
, ,

array exist

1, (
), 0 ( )

array get

, (1, 3 . .) ,

290

VI. TCL/Tk
24.6 ()

array set

. array get,
. . ,

array size

array names []


. , ,

:
array set users [list \
{1} { } \
{2} { } \
{3} { }];
puts " users [array size users] ";
puts " 3 : $users(3)";

:
foreach id [array names users] {
puts "$users($id) = $id";
}

24.5.
TCL-
, , . . TCL . , C
, Basic, Pascal, PHP, Java. ,
(, C PHP),
TCL .
$, . C
$ , , . PHP , $
:
.

24. TCL

291

TCL, , ,
"" , $.
:
set s1 = "string";
set s2 = "string";
if {s1 eq s2} {
puts { s1 s2 };
} else {
puts { s1 s2 };
}

( , s1 s2 )
. ? $
. , . . TCL , $.
string, , :
set s "Privet";
set new_s [string replace s 1 5 "Hello"];
puts $new_s;

, "PHello",
s. $ s, :
set new_s [string replace $s 1 5 "Hello"];

, . , , , , ,
.
TCL-
if :
if ($new_s eq "Hello") { puts "- " }

, if , , ,
. :
if {$new_s eq "Hello"} { puts "- " }

: if , TCL . , TCL- ,
.

25


25.1.
open:
open _ [_] [_]

, .
(. 25.1). ,
: , . . C- fopen().
25.1.

r+

. , ;
,

w+

. , ;
,

. . ,

a+

( ). ,

UNIX-. , . ,
" ".
open ,
/ . -

25.

293

: stdout ( ), stdin ( ) stderr (


).
close, :
close id

:
set fId [open test.txt r];
puts " test.txt , ID $fId";
close $fId;

:
if {[catch {set fId [open test.txt r+]} err]} {
puts " , : $err";
return 1;
} else {
puts " test.txt , ID $fId";
close $fId;
}

25.2.
:
gets ;
read , EOL (End Of

Line, ), .
, ;
scan .

gets. , :
set line "";
gets stdin line;
puts $line;

line, , .
. ,
test.txt. ,
, .
gets:
1 (, ). get.tcl 25.1.

294

VI. TCL/Tk

25.1. get.tcl
set fId [open test.txt r];
set tChars 0;
set tLines 0;
while {[set
puts
incr
incr
}

count [gets $fId line]] != -1} {


"($count ) $line"
tChars $count
tLines

puts " $tChars "


puts " $tLines "
close $fId

while "" tChars (


) tLines ( ).
. 25.1.
read:
read id_ [_]

. 25.1. get.tcl

25.

295

read , . , open.
, read. read
, (EOF)
. , read
.
:
set fId [open test.txt r];
set input [read $fId];
puts " [string length $input] ";
close $fId;

input, ,
. 512 :
set fId [open test.txt r];
while {![eof $fId]} {
set input [read $fId 512]
puts " [string length $input] : $input"
}
close $fId;

, read , gets,
read.
: , . read
: .
1024 2048 .
gets read ,
scan .

25.3.
puts. :
puts [-nonewline] [ID_]

puts . , , . -nonewline
.
.
, -nonewline,
puts , .

296

VI. TCL/Tk

, , :
\n (UNIX, Linux, MacOS X);
\r ( MacOS OS X);
\r\n (Windows).

,
, TCL ( Linux, TCL
). , puts
, :
-nonewline (puts
"Hello\r");
fconfigure. , :
http://www.tcl.tk/man/tcl8.4/TclCmd/fconfigure.htm.
puts format
(. 24) .

/ , , .
fflush:
fflush ID_

25.4.

:
. TCL.
tell seek:
tell ID_
seek ID_ []

. . , .
:
start ;
end ;
current .

TCL ,

.

26

26.1. Tk-
- "", TCL-. 23
, ,
( 26.1).
26.1.
#!/usr/bin/wish
label .l -width [string length "My First Tk-application"] -text "My First
Tk-application";
button .b -text "Exit" -command exit;
pack .l -padx 40 -pady 10
pack .b -padx 40 -pady 10

TCL, .
. tclsh wish.
, ,
:
#!/usr/bin/tclsh

:
#!/usr/bin/wish

, , TCL- , .
:
tclsh < >

VI. TCL/Tk

298

wish < >

,
Exit. label button
, pack
.

: , , ,
. . .

: . Tk 45 , .
Tk- .
, ,
(
onClick). , . Exit
exit, . , .
, . ,
, , , . . . TCL- exit
, . .
,
. . . 26.1
, "" , , . . . 26.2 .
, Tk- ,
. 26.2. , . 26.2
, .
.
26.1.

button

canvas

checkbutton

()

entry

26.

299
26.1 ()

frame

label

( )

labelframe

,
(label)

listbox

menu

menubutton

message

( )

panedwindow

()

radiobutton

scale

( ,
, )

scrollbar

spinbox

text

toplevel

(),

26.2.

-activebackground

(
, )

-activeborderwidth

( )

-activeforeground

-anchor

( n,
ne, e, se, s, sw, w, nw center)

-background

-bd

-borderwidth

-bg

-background

-bitmap

BMP-

-borderwidth

-compound

BMP-
( : bottom, top, left, right, center)

-cursor

VI. TCL/Tk

300

26.2 ()

-disabledforeground

-exportselection

,
X-

-fg

-foreground

-font

-foreground

-highlightbackground

-highlightcolor

-highlightthickness

-image

, -bitmap
-text

-justify

. :
left, right center

-padx

-pady

-relief

3D- , flat, groove, raised, ridge,


sunken solid

-selectforeground

-text

-wraplength

: ,

26.2. Tk-

. (, , ), , Tk-. "" ,
-.
, Windows,
MacOS Linux , .

Linux TCL/Tk , Windows MacOS
http://www.tcl.tk/software/tcltk/8.0.html.

26.

301

TCL/Tk Windows, , GNOME KDE. .


Tk- , , :
.
. .l, .b:
label .l -width [string length "My First Tk-application"] -text
"My First Tk-application";
button .b -text "Exit" -command exit;

?
, button1 label1?
, , "." (). ,
,
. ,
.button1:
button .button1 -text "Exit" -command exit;

( Tk ,
)! ,
, : .l.small1 .l.small2.
, .l , .l, , ,
(.).
( ),
, . . , X.Org
.

27



27.1. pack
TCL-.
,
. TCL pack, grid place. grid , pack, , place. , ,
Tk. , pack,
.
, pack,
, , .
pack ,
. -in (), -before ()
-after () .
, .
, (, , ).
first.tcl :
pack .b -padx 40 -pady 10 -before .l

-before .l ,
. . 27.1.
, pack . , (cavity).
.

27.

303

. 27.1.

, -side. -side top


bottom, ,
, -ipady -pady. -side left right,
, , -ipadx -ipad. -expand;
. , -

, 2.
( )
-fill;
. -

, -anchor;
. -

, . , , , .
, ( ) . , .
pack
(. 27.1). . 27.1 pack, (man pack).
27.1. pack

-after

-ahchor

, c
()

-before

-expand 1|0

, (1)
- (0)

304

VI. TCL/Tk
27.1 ()

-fill

- ,
:
none ,
( );
x ;
y ;
both

-in

-ipadx

, . , 1 (1 ), , 1c (0,1 ).
0

-ipady

.
0

-padx

.
0

-pady

. 0

-side

, - :
left ;
right ;
top ;
bottom .
top

forget

"" ,

slaves

27.2. button
button . :
button

, button . 27.2.
27.2. button

-command

, .
TCL-,

27.

305
27.2 ()

-default

:
normal ;
active ;
disabled

-height

-state

:
normal ;
active ;
disabled

-width

invoke

, -command.
,

configure

flash

. Activate Exit. Exit ,


Activate Exit ( 27.1).
27.1. buttons.tcl
set bExit [button .e -width 20 -text "Exit" -state disabled \
-command exit]
set bActivate [button .a -width 20 -text "Activate" \
-command {$bExit configure -state normal}]
pack $bActivate -pady {0 20}
pack $bExit

. Exit,
(-state disabled). Activate. Activate:
$bExit configure -state normal
$bExit

, Exit.
configure
. button .e -state normal, .e, -

306

VI. TCL/Tk

. configure.
, ,
. 27.2.

. 27.2. buttons.tcl

. Exit ,
Activate Flash, Exit ( 27.2). , , .
27.2. flash_buttons.tcl
set bExit [button .e -width 20 -text "Exit" \
-command exit]
set bFlash [button .a -width 20 -text "Flash" \
-command {$bExit flash}]
pack $bFlash -pady {0 20}
pack $bExit

27.

307

27.3. checkbutton
() checkbutton:
checkbutton

button, checkbutton (. 27.3).


27.3. checkbutton

-command

, .
TCL-,

-height

-indicatoron

-offvalue

, , .
0

-onvalue

, , .
1

-selectcolor

-state

: normal, active, disabled

-variable

, .
,

-width

cget

configure

flash

invoke

, -command

select

,
-variable, ,
-onvalue

deselect

,
-variable, ,
-offvalue

toggle

.
,

, . :
set ckFirst [checkbutton .ckfirst -text " " \
-command {GetState .ckfirst}]
set ckSecond [checkbutton .cksecond -text " " \

308

VI. TCL/Tk

-command {GetState .cksecond}]


set ckThird [checkbutton .ckthird -text " " \
-offvalue "OFF" -onvalue "ON" -command {GetState .ckthird}]

: ckFirst, ckSecond ckThird, .ckfirst, .cksecond, .ckthird. : GetState, . GetState , (


). , ,
1, 0. -onvalue -offvalue
, .
, "ON", "OFF". GetState :
proc GetState {ckbuttons} {
foreach ckbutton $ckbuttons {
set var [$ckbutton cget -variable]
global $var
set val [set $var]
puts "$var = $val" }
}

$ckbutton
cget -variable.
ckbuttons,
:
set ckbuttons [list $ckFirst $ckSecond $ckThird]

:
Toggle toggle , -

;
Clear ;
Set ;
;
.

:
set bToggleAll [button .toggleall -width 12 -text " Toggle" \
-command {ButtonCommand toggle $ckbuttons}]
set bClearAll [button .clearall -width 12 -text " Clear" \
-command {ButtonCommand clear $ckbuttons}]
set bSetAll [button .setall -width 12 -text " Set" \

27.

309

-command {ButtonCommand set $ckbuttons}]


set bShowAll [button .showall -width 12 -text "" \
-command {GetState $ckbuttons}]
set bExit [button .exitb -width 12 -text "" \
-command exit]

ButtonCommand,
,
, ckbuttons ( ). GetState ckbuttons,
. . . .
ButtonCommand :
proc ButtonCommand {action ckbuttons} {
foreach ckbutton $ckbuttons {
switch $action \
toggle { $ckbutton toggle } \
clear { $ckbutton deselect } \
set { $ckbutton select } }
}

switch,
. , ,
, .
27.3.
27.3. check.tcl
proc ButtonCommand {action ckbuttons} {
foreach ckbutton $ckbuttons {
switch $action \
toggle { $ckbutton toggle } \
clear { $ckbutton deselect } \
set { $ckbutton select } }
}
proc GetState {ckbuttons} {
foreach ckbutton $ckbuttons {
set var [$ckbutton cget -variable]
global $var
set val [set $var]
puts "$var = $val" }
}
set ckFirst [checkbutton .ckfirst -text " " \
-command {GetState .ckfirst}]

310

VI. TCL/Tk

set ckSecond [checkbutton .cksecond -text " " \


-command {GetState .cksecond}]
set ckThird [checkbutton .ckthird -text " " \
-offvalue "OFF" -onvalue "ON" -command {GetState .ckthird}]
set ckbuttons [list $ckFirst $ckSecond $ckThird]
set bToggleAll [button .toggleall -width 12 -text " Toggle" \
-command {ButtonCommand toggle $ckbuttons}]
set bClearAll [button .clearall -width 12 -text " Clear" \
-command {ButtonCommand clear $ckbuttons}]
set bSetAll [button .setall -width 12 -text " Set" \
-command {ButtonCommand set $ckbuttons}]
set bShowAll [button .showall -width 12 -text "" \
-command {GetState $ckbuttons}]
set bExit [button .exitb -width 12 -text "" \
-command exit]
pack $ckFirst $ckSecond $ckThird -anchor w
pack $bToggleAll -pady 5 -padx 5 -side left
pack $bClearAll $bSetAll $bShowAll $bExit -pady 5 -padx {0 5} -side left

. 27.3. check.tcl

27.

311

. 27.3 .
. 2 3, :
cksecond = 1
ckthird = ON

:
ckfirst = 0
cksecond = 1
ckthird = ON

27.4.
, . , , . ,
. ,
.
radiobutton.
, checkbutton.
radiobutton . ,
.
, .
:
set rRed [radiobutton .rred -text "" -value red]
set rBlue [radiobutton .rblue -text "" -value blue]
set rGreen [radiobutton .rgreen -text "" -value green]

radioButtons, :
set radioButtons [list $rRed $rGreen $rBlue]

:
set labelColor [label .lcolor -text " "]
set bSet [button .bset -width 15 -text " " \
-command {SetColor $selectedButton}]
set bExit [button .bexit -width 15 -text "" -command exit]

setColor,
. setColor -

312

VI. TCL/Tk

. "" bSet, :
$rRed select
$bSet invoke

27.4. radio.tcl
. 27.4.

. 27.4.
radio.tcl

27.4. radio.tcl
proc SetColor {newColor} {
. configure -background $newColor
global labelColor
$labelColor configure -background $newColor
global radioButtons
foreach button $radioButtons {
$button configure -background $newColor \
-activebackground $newColor \
-highlightbackground $newColor }
}
set rRed [radiobutton .rred -text "" -value red]
set rBlue [radiobutton .rblue -text "" -value blue]
set rGreen [radiobutton .rgreen -text "" -value green]
set radioButtons [list $rRed $rGreen $rBlue]
set labelColor [label .lcolor -text " "]
set bSet [button .bset -width 15 -text " " \
-command {SetColor $selectedButton}]
set bExit [button .bexit -width 15 -text "" -command exit]

27.

313

$rRed select
$bSet invoke
pack $labelColor -anchor w
pack $rRed $rGreen $rBlue -pady 0 -padx {2 0} -anchor w
pack $bSet -pady {10 2} -padx 5
pack $bExit -pady {2 10} -padx 5

27.5.
menu. :
set mainMenu [menu .mainmenu]

, :
set mFile [menu $mainMenu.mFile -tearoff 0]
$mainMenu add cascade -label "" -menu $mFile

:
$mFile add command -label "..." -command {Cmd Open}
$mFile add command -label "" -command {Cmd Close}

add command label,


, command.
Cmd TCL-,
.
add separator:
$mFile add separator

,
( 27.5). . 27.5.
27.5. menu.tcl
set mainMenu [menu .mainmenu]
. configure -menu $mainMenu
set mFile [menu $mainMenu.mFile -tearoff 0]
$mainMenu add cascade -label "" -menu $mFile
$mFile
$mFile
$mFile
$mFile
$mFile
$mFile
$mFile
$mFile
$mFile
$mFile

add
add
add
add
add
add
add
add
add
add

command -label
command -label
command -label
command -label
separator
command -label
command -label
separator
command -label
command -label

"..." -command {Cmd CreateFile}


"..." -command {Cmd Open}
"" -command {Cmd Save}
" " -command {Cmd SaveAs}
"" -command {Cmd Print}
" " -command {Cmd PrintSetup}
"" -command {Cmd Close}
"" -command exit

314

VI. TCL/Tk

set mEdit [menu $mainMenu.mEdit -tearoff 0]


$mainMenu add cascade -label "" -menu $mEdit
$mEdit add command -label "" -command {Cmd "Copy"}
$mEdit add command -label "" -command {Cmd "Cut"}
$mEdit add command -label "" -command {Cmd "Paste"}
$mEdit add separator
$mEdit add command -label "" -command {Cmd "Search"}
$mEdit add command -label "" -command {Cmd "Replace"}
proc Cmd {cmd} {
tk_messageBox -icon info -type ok -message $cmd
}

. 27.5. menu.tcl

. exit,
. Cmd,
puts tk_messageBox, , -message. .

27.

315

27.6.
Tk : entry spinbox. , . , .
entry spinbox ,
. 27.4. ""
, .
27.4. entry spinbox

spinbox

-buttonbackground

spinbox

-buttoncursor

,
spinbox'

spinbox

-command

, ,

-exportselection

true,
X-

-format

.
%<pad>.<pad>f

spinbox

-from

-insertbackground

-insertborderwidth

-insertofftime

0, off

-insertontime

0, on

-insertwidth

( )

-invcmd

, ,
-validatecommand 0

spinbox

-increment

-from -to.
, ,
0 20 2. -from
0, -to 20,
increment 2

spinbox

-readonlybackground

, ( )

-selectbackground

-selectforeground

VI. TCL/Tk

316

27.4 ()

entry

-show


, *.

-textvariable

,
-text. -text

spinbox

-to

-validate

:
none ( );
focus
, ;
focusin
, ;
focusout
, ;
key ;
all

-vcmd

, , -validate none.
-vcmd: -validatecommand

-values

. spinbox
, , -from, -to -increment

. 27.4 entry spinbox,


. :
man entry
man spinbox

, -vcmd. . 27.5.
27.5.

%d

(0 , 1 , 1 )

%i

%P

27.

317
27.5 ()

%s

%S

%v

(none, all, focus . .)

%W

, . , .
.
(,
), .
27.6.
#
proc Letter {text} {
if {[regexp {[^A-Z-]} $text]} {
.a configure -bg red
return 0
} else {
.a configure -bg white
return 1
}
}
#
proc Digit {text} {
if {[regexp {[^0-9]} $text]} {
.d configure -bg red
return 0
} else {
.d configure -bg white
return 1
}
}

label .la -text " :"


entry .a -bg white -textvariable a \
-invcmd bell -validate all -vcmd {Letter %P}
pack .la .a -fill x

318

VI. TCL/Tk

label .ld -text ":"


entry .d -bg white -textvariable d \
-invcmd bell -validate all -vcmd {Digit %P}
pack .ld .d -fill x

entry.tcl . 27.6.

. 27.6.
entry.tcl

27.7.
listbox. , . . 27.7.
27.7. list.tcl
#
proc GetCars {carsfile} {
set fileId [open $carsfile r]
while {[gets $fileId line] > 0} {
lappend cars [string trim [lrange $line 0 end]]
}
close $fileId
return $cars
}
# ,
listbox .carslist -bg white
#
set cars [GetCars "cars.txt"]
foreach car $cars {
.carslist insert end $car
}
# ""
button .bexit -text "" -command exit
grid .carslist -padx 5 -pady 5 -sticky nsew
grid .bexit -pady {0 5}

27.

319

(. 27.7) ,
. pack grid,
.

. 27.7.
list.tcl

listbox (),
scrollbar ( ) text ( ).
, . /usr/share/tk8.6/demos (
Tk , ).
, , TCL, .
( ).

27.8. .
bind
, , ( Tk) . bind , (. 27.6) :
bind

, bind .
(, ) , , .
27.6.

Active

ButtonPress

, Button
ButtonPress. ButtonPress .
.
ButtonPress ,

320

VI. TCL/Tk
27.6 ()

ButtonRelease

Configure

Deactivate

Destroy

(, )

Enter

Expose

FocusIn

FocusOut

""

KeyPress

, .
Key

KeyRelease

Leave

Map

, (,
, )

Motion

MouseWheel

Unmap

, ,

Visibility

, ,

28


28.1. grid
, .
: , -. ,
grid, . .
grid ,
, pack.
grid :
. , , ;
-row -column.

28.1.1.
,
grid , . , "" .
, , , .
, .
. , 12 34 ( 28.1).
28.1. grid
wm title . ""
for {set i 1} {$i <= 12} {incr i} {

VI. TCL/Tk

322

frame .fr$i -bg white -width .50i -height .50i


label .l$i -bg blue -fg white -text $i
grid propagate .fr$i false
grid .l$i -in .fr$i
if {![expr $i % 3]} {
grid .fr[expr $i 2] .fr[expr $i -1] .fr$i -padx 5 -pady 5
}
}

, . , (, ) wm.
for 12 .frN, N ,
, -width
-height. .lN (N
), . -in grid :
grid .l$i -in .fr$i

-in .

( ):
grid propagate .fr$i false

. 28.1. grid.tcl

28.

323

, . . propagate
true.
(. . ) grid $i 2, $i 1 $i: -padx -pady. .
. 28.1.

28.1.2.

. -row -column . 28.2 :
, . , row, -row grid. ,
, .
28.2. grid
wm title . " 2"
set row 1
for {set i 1} {$i <= 12} {incr i} {
frame .fr$i -bg white -width .50i -height .50i
label .l$i -bg blue -fg white -text $i
grid propagate .fr$i false
grid .l$i -in .fr$i
if {![expr $i % 3]} {
grid .fr[expr $i 2] -row $row -column 0 -padx 5 -pady 5
grid .fr$i -row $row -column 2 -padx 5 -pady 5
grid .fr[expr $i 1] -row $row -column 1 -padx 5 -pady 5
incr row
}
}

, . 28.2.

43 , , . 28.3. 28.3.
28.3. grid3.tcl
wm title . " 3"
set counter 1

324

VI. TCL/Tk

for {set i 1} {$i <= 12} {incr i} {


frame .fr$i -bg white -width .50i -height .50i
label .l$i -bg blue -fg white -text $i
grid propagate .fr$i false
grid .l$i -in .fr$i
if {![expr $i % 3]} {
grid .fr[expr $i 2] -column $counter -row 0 -padx 5 -pady 5
grid .fr[expr $i 1] -column $counter -row 1 -padx 5 -pady 5
grid .fr$i -column $counter -row 2 -padx 5 -pady 5
incr counter
}
}

. 28.2. grid2.tcl

. 28.3. grid3.tcl

28.

325

28.1.3.
- Web-, , HTML .
( -
) ( ).
HTML, Tk -rowspan
-columnspan grid:
-rowspan ,

;
-columnspan , -

.
, . grid ,
. , -rowspan -columnspan,
28.4, . 28.4,
.
28.4. span.tcl
label
label
label
label
label
label
grid
grid
grid
grid

.l1
.l2
.l3
.l4
.l5
.l6

.l1
.l2
.l3
.l4

-bg
-bg
-bg
-bg
-bg
-bg

red
red
red
red
red
red

-width
-width
-width
-width
-width
-width

10
10
10
10
10
10

-height
-height
-height
-height
-height
-height

2
2
2
2
2
2

-relief
-relief
-relief
-relief
-relief
-relief

groove
groove
groove
groove
groove
groove

-text
-text
-text
-text
-text
-text

"Label
"Label
"Label
"Label
"Label
"Label

1"
2"
3"
4"
5"
6"

-row 0 -column 0 -columnspan 2 -sticky nsew


-row 0 -column 2 -rowspan 2 -sticky nsew
-row 1 -column 0 -columnspan 2 -sticky nsew
.l5 .l6 -sticky nsew

. 28.4.
span.tcl

, -sticky,
. (
), -sticky
. -sticky

326

VI. TCL/Tk

. n, s, e w ( ,
).
(n , s , e , w ), "" .
(n s e
w), , .
, -sticky
pack: -anchor -fill. ,
.

28.2.
frame () .
, ,
grid. .
,
.
-relief. frames.tcl ( 28.5)
.
28.5. frame.tcl:
frame .f1 -width 1i -height .25i -relief raised -borderwidth 2
label .l1 -text "raised"
frame .f2 -width 1i -height .25i -relief flat -borderwidth 2
label .l2 -text "flat"
frame .f3 -width 1i -height .25i -relief sunken -borderwidth 2
label .l3 -text "sunken"
frame .f4 -width 1i -height .25i -relief groove -borderwidth 2
label .l4 -text "groove"
frame .f5 -width 1i -height .25i -relief solid -borderwidth 2
label .l5 -text "solid"
frame .f6 -width 1i -height .25i -relief ridge -borderwidth 2
label .l6 -text "ridge"
set row 0
foreach num {1 2 3 4 5 6} {
grid .f$num
grid .l$num -in .f$num -sticky nsew
grid propagate .f$num false
grid rowconfigure . $row -pad 5

28.

327

incr row
}
grid columnconfigure . 0 -pad 5

( )
( -relief,
) .fN, N
. , .
foreach
.
. 28.5. ,
.
. 28.5. frame.tcl

28.3.
- .
, . ( 28.6)
- .
: . ,
, ,
(. 28.6).

. 28.6. child.tcl

328

VI. TCL/Tk

toplevel:
toplevel []

, : ,
, . .
28.6.
proc ShowChild {} {
toplevel .w
wm title .w " "
label .w.l -justify left -height 1 -width 0 -text " "
button .w.b -text "" -command {wm withdraw .w}
grid .w.l -sticky w
grid .w.b -sticky s -pady {30 10}
}
set win [button .win -text "" -command {ShowChild}]
set ext [button .ext -text "" -command exit]
grid $win $ext -padx 5 -pady 5

ShowChild.
ShowChild :
.w;
.w;
.w.l;
( , -

);
grid.

28.4.
-
. toplevel
. : . ( ),
message.
, tk_mesagebox.
"" . , , tk_messagebox.
, message:

28.

329

message .m -text " \n message"


grid .m

, message (. 28.7) .
tk_messageBox .
. 28.1.
28.1. tk_messageBox

-default

(ok, cancel).
-type. -default ,

-icon

. error, info, question warning


. ,

-message

-parent

-title

-type

( ):
abortretryignore Abort, Retry Ignore;
ok OK;
okcancel OK Cancel;
retrycancel Retry Cancel;
yesno Yes No;
yesnocancel Yes, No, Cancel

:
set answer [tk_messageBox -message "?" -type yesno -icon question]
case $answer {
yes {tk_messageBox -message " !" -type ok}
no { exit }
}

. 28.8.

. 28.7. message

. 28.8. tk_messageBox

330

VI. TCL/Tk

28.5.

tk_getOpenFile tk_getSaveFile:
tk_getOpenFile
tk_getSaveFile

. 28.2.
28.2.

-defaultextension

.
, .

-filetypes __

.
, (
),
. ,

-initialdir

-initialfile _

,
. tk_getOpenFile

-parent

-title

:
set types {
{{ JPEG} {.jpg} }
{{ GIF} {.gif} }
{{ PNG} {.png} }
{{ } * }
}
set filename [tk_getOpenFile -filetypes $types -initialdir ~]
if {$filename != ""} {
# filename ,
}

/ , , . ,

28.

331

, ,
. . 28.9.

. 28.9.

29


29.1.

nmap. . ,
nmap . , ,
, " " .
(, Linux- nmap),
,
nmap.
nmap :
nmap [] ___

nmap , nmap (
), -O (
) -sV ( ).
:
_-_

:
192.168.0.1-192.168.0.100

nmap . .
( entry),
( radiobutton). .
, .

29.

333

, : nmap, : ,
. nmap
. , nmap, ( ) .
? puts,
. text, , ,
( text ). nmap
text. ,
.

29.2.
nmap exec:
exec nmap $options $address

:
set nmapOutput [exec nmap $addr $aa]

nmapOutput
:
puts $nmapOutput
.t insert end $nmapOutput

, ,
. 29.1 .
"-". ,
.
:
set rNormal [radiobutton .rnormal -text " " -value ""]
set rOs [radiobutton .ros -text " " -value "-O"]
set rServices [radiobutton .rservices -text " " -value "-sV"]

-value:
. nmap.
radioButtons, aa - .
set radioButtons [list $rNormal $rOs $rServices]
set aa ""
set labelHint [label .lcolor -text " "]

aa . aa
. , -

334

VI. TCL/Tk

aa :
set Address [entry .address -textvariable aa]

text :
set OutputWidget [text .t -setgrid true \
-width 80 -height 20 -wrap word]
set bSet [button .bset -width 15 -text "" \
-command {ScanNmap $selectedButton}]
set bExit [button .bexit -width 15 -text "" -command exit]

. 29.1. nmap

ScanNmap, :
proc ScanNmap {opt} {
global aa;
set nmapOutput [exec nmap $opt $aa]
#puts $nmapOutput
.t insert end $nmapOutput
}

29.

335

opt , nmap.
aa.
nmap .t. , .
"" :
$rNormal select
pack $labelHint -anchor w
pack $Address -anchor w
...

29.1.
29.1. nmap.tcl
proc ScanNmap {opt} {
global aa;
set nmapOutput [exec nmap $opt $aa]
#puts $nmapOutput
.t insert end $nmapOutput
}
set rNormal [radiobutton .rnormal -text " " -value ""]
set rOs [radiobutton .ros -text " " -value "-O"]
set rServices [radiobutton .rservices -text " " \
-value "-sV"]
set radioButtons [list $rNormal $rOs $rServices]
set labelHint [label .lcolor -text " "]
set aa ""
set Address [entry .address -textvariable aa]
set OutputWidget [text .t -setgrid true \
-width 80 -height 20 -wrap word]
set bSet [button .bset -width 15 -text "" \
-command {ScanNmap $selectedButton}]
set bExit [button .bexit -width 15 -text "" -command exit]
$rNormal select
pack
pack
pack
pack
pack
pack

$labelHint -anchor w
$Address -anchor w
$rNormal $rOs $rServices -pady 0 -padx {2 0} -anchor w
$OutputWidget
$bSet -pady {10 2} -padx 5
$bExit -pady {2 10} -padx 5

336

VI. TCL/Tk

29.3.
root, root, nmap:
sudo wish nmap.tcl

sudo, su:
su -c wish nmap.tcl

29.4.
. . ? , , text ,
.
nmap, man nmap.

VII

GTK+
30.

31.

GTK+

32.

33.

Glade

C
TCL, ,
Tk. GTK+, C.
GLib Glade.

30


30.1. GTK+
C .
TCL/Tk . , Tk , TCL , TCL/Tk . - , ,
, C .
TCL/Tk .
, , , GTK+. GTK+ ( GTK)
GIMP, The GIMP Toolkit.

GNOME. GTK GNOME.
, , , , . GTK
GNOME, LXDE
Xfce.
GTK -: , GTK, Windows.
: , ,
, GTK, .
GTK- , GTK . , ,
GIMP Linux- (
KDE, Qt,
GIMP). Windows
: http://www.gtk.org/download-windows.html.

30.

339

GTK GLib GDK (The GIMP Drawing Kit).


,
GTK. X.Org .
GLib,
GTK-.
glib.h.

30.2. GLib
30.2.1.
GTK- , GLib. , , (, ),
, .
C
? ,
. ,
int 32-, 64-.
, gint ( GLib), GLib GLib, .
. 30.1 C
GLib.
30.1. GLib
C

GLib

char

gchar

short

gshort

long

glong

int

gint

unsigned char

guchar

unsigned short

gushort

unsigned long

gulong

unsigned int

guint

float

gfloat

double

gdouble

long double

gldouble

boolean

gboolean

void*

gpointer

VII. GTK+

340

30.2.2. GLib
GLib ,
. 30.2 , , ,
.
30.2. GLib

gchar* g_strchug (gchar* string)

string,
( ).

gchar* g_strchomp(gchar* string)

string (, . .),

void g_strdown (gchar* string)

string

void g_strup (gchar* string)

string

void g_strreverse (gchar* string)

: . .

gchar *g_strconcat (const gchar


*string1, ...);

, , .

gchar *g_strjoin (const gchar


*separator, ...);

,
,
.
,

gchar *g_strdup (const gchar*


string);

.
,
string.

gchar *g_strndup (const gchar


*string, gsize n);

, g_strdup(), n

gchar **g_strdupv (gchar **strings);

strings. , , g_strfreev()

gchar *g_strcpy (gchar *dest, const


gchar* src);

src dst. \0

gchar *g_strnfill (gsize length,


gchar fill_char);

length ,
fill_char

void g_strfreev (gchar **strings);

void g_print (const gchar *string);

string

30.

341
30.2 ()

gint g_printf (const gchar


*format, ...);

printf()

gint g_sprintf (gchar *buf, const


gchar *format, ...);

sprintf()

gint g_snprintf (gchar *buf, gulong


n, const gchar *format, ...);

snprintf()

gint g_strcasecmp (const gchar *s1,


const gchar *s2);

strcasecmp()

gint g_strncasecmp (const gchar *s1,


const gchar *s2, guint n);

strncasecmp()

gboolean g_ascii_isalnum (gchar c)

true, c

gboolean g_ascii_isalpha (gchar c)

true, c

gboolean g_ascii_iscntrl (gchar c)

true, c

gboolean g_ascii_isdigit (gchar c)

true, c

gboolean g_ascii_isgraph (gchar c)

true, c

gboolean g_ascii_islower (gchar c)

true, c

gboolean g_ascii_isupper (gchar c)

true, c

gboolean g_ascii_isprint (gchar c)

true, c
()

gboolean g_ascii_ispunct (gchar c)

true, c

gboolean g_ascii_isxdigit (gchar c)

true, c

GLib
:
http://developer.gnome.org/glib/2.29/glib-String-Utility-Functions.html

30.2.3.
GLib .
:
gpointer g_malloc( gulong size );
gpointer g_realloc( gpointer mem, gulong size );
void g_free( gpointer mem );

342

VII. GTK+

30.2.4.
GLib - .
gslist.h (GLib Single List)
, glist.h .
,
.
- :
//
typedef struct _GSList GSList;
struct _GSList
{
gpointer data;
GSList *next;
//
}
//
typedef struct _GList GList;
struct _GList
{
gpointer data;
GList *next;
//
GList *prev;
//
}

data , , gpointer void*.


, . :
GList *list = NULL;
GSList *slist = NULL;

.
g_list_append() g_slist_prepend()
:
gchar *element1 = g_strdup(" ");
list = g_list_append(list, element1);

g_list_append() g_slist_prepend() .
, :
g_list_prepend(GList *list, gpointer data)
g_slist_prepend(GSList *list, gpointer data)

:
GList *g_list_insert( GList *list, gpointer data, gint position )
GSList *g_slist_insert( GSList *list, gpointer data, gint position )

30.

343

position , . position 0, .
:
GList *g_list_remove(GList *list, gpointer data )
GSList *g_slist_remove(GSList *list, gpointer data)

:
g_list_nex(), g_slist_next() "" ;
g_list_prev() .


.
//
GList *list = double_list;
//
...
//
while (list!=NULL)
{
g_printf("%s\n",list->data);
list = g_list_next(list);
}

:
void g_list_free(GList *list);
void g_slist_free(GSList *slist);

:
GSList *g_slist_sort(GSList * slist, GCompareFunc f);

, .
. :
typedef gint (*GCompareFunc) (gconstpointer a, gconstpointer b);

.
:
a<b, 1 (, 0);
a==b, 0;
a>b, 1 ( 0).

GLib , ,
.

344

VII. GTK+

30.2.5.
. gtimer.h.
g_timer_new():
GTimer *g_timer_new()

g_timer_start():
GTimer *timer = g_timer_new();
g_timer_start(timer);

g_timer_elapsed() ( ), ( ,
microseconds):
gdouble g_timer_elapsed( GTimer *timer,
gulong *microseconds );

g_timer_reset():
g_timer_reset(GTimer *timer)

g_timer_stop(), g_timer_destroy():
g_timer_stop(GTimer *timer)
g_timer_destroy(GTimer *timer)

30.1 . , . 10 . , GLib
, ,

.
30.1.
#include <stdio.h>
#include <glib.h>
#include <gtimer.h>
int main()
{
gdouble sec;
gulong ms;
gint i;
printf(" \n ");

30.

345

//
GTimer *timer = g_timer_new();
g_timer_start(timer);
for (i=1; i>0;)
{
sec = g_timer_elapsed(timer, &ms);
g_printf(" %d\n", i);
if (sec >=10)
{
g_timer_stop(timer);
printf(" . : %d\n",ms);
break;
}
i++;
}
g_timer_destroy(timer);
return 0;
}

, GLib,
GTK-,
.

31

GTK+
31.1. , ,
,
GTK+, . - , ,
Tk.
: , , ,
. . . .
( ).
Tk (pack, grid), .
.
.
, . Tk
, , Linux
. GTK
. ,
button_press_event, ,
(, GDK_1BUTTON_PRESS
). .
:
1. GTK.
2. , .
3. , .
4. .
5. .

31. GTK+

347

:
GtkWidget *button;
...
/* "!" */
button = gtk_button_new_with_label ("!");
/* :
hello() */
gtk_signal_connect (GTK_OBJECT (button), "clicked",
GTK_SIGNAL_FUNC (hello), NULL);
/* */
gtk_container_add (GTK_CONTAINER (window), button);
/* */
gtk_widget_show (button);

. hello()
window ( ) .
gtk_widget_show(), .

31.2.
GTK-:
. , GTK , .
gtk.h:
#include <gtk/gtk.h>

main()
GTK:
GtkWidget *window1;
gtk_init( &argc, &argv );

. 31.1
GTK-.
31.1. GTK-
#include <gtk/gtk.h>
int main( int
argc, char *argv[] )
{
GtkWidget *window1;

VII. GTK+

348
gtk_init( &argc, &argv );
window1 = gtk_window_new( GTK_WINDOW_TOPLEVEL );
gtk_window_set_title(GTK_WINDOW(window1),"My App");
gtk_widget_show( window1 );
gtk_main();
return 0;
}

gtk_window_new() , gtk_window_set_title()
.
gtk_main(). gtk_main() ,
. gtk_init() gtk_main() GTK.

31.3.
GTK- first.c.
:
gcc first.c -o first `gtk-config --cflags` `gtk-config --libs`


, Makefile, ,
.

. 31.1. GTK+

31. GTK+

349

, , gtk.h gtk-config (. 31.1).


libgtk+-devel
(. 31.2),
(. 31.3).

. 31.2. libgtk+-devel

. 31.3.

VII. GTK+

350

. 31.4.

. 31.5. GTK-

31. GTK+

351

,
. 31.4. ,
.
:
./first

My App (. 31.5).

31.4. .

. , ( ) , .
""! . ( ), ,
. , , ,
, (. 31.6):
ps -ax | grep first

. 31.6. ps: first

kill (kill < >).


, . : , ,
. gtk_main_quit() destroy window1:
gtk_signal_connect( GTK_OBJECT( window1 ), "destroy",
GTK_SIGNAL_FUNC( gtk_main_quit ), NULL );

31.1,
, , gtk_signal_connect():
:
window1 = gtk_window_new( GTK_WINDOW_TOPLEVEL );
gtk_signal_connect( GTK_OBJECT( window1 ), "destroy",
GTK_SIGNAL_FUNC( gtk_main_quit ), NULL );
gtk_window_set_title(GTK_WINDOW(window1),"My App");
gtk_widget_show( window1 );

VII. GTK+

352

. .
gtk_main_quit() ,
. - , , . .
gtk_main_quit().
31.2.
31.2.
#include <gtk/gtk.h>
/* - */
void close_window1( GtkWidget *widget, gpointer data);
int main( int
argc, char *argv[] )
{
GtkWidget *window1;
gtk_init( &argc, &argv );
window1 = gtk_window_new( GTK_WINDOW_TOPLEVEL );
gtk_signal_connect( GTK_OBJECT( window1 ), "destroy",
(GtkSignalFunc)close_window1, &window1 );
gtk_widget_show( window1 );
gtk_main();
return( 0 );
}
/* gtk_main_quit() */
void close_window1( GtkWidget *widget, gpointer data)
{
gtk_main_quit();
}

, gtk_window_set_default_size():
void gtk_window_set_default_size(GtkWindow *window,
gint width,
gint heigth);

window width, heigth.

31. GTK+

353

gtk_widget_set_uposition():
void gtk_widget_set_uposition(GtkWindget *widget,
gint coord_x,
gint coord_y);

. , .
gtk/gtkwindow.h,
gtk/gtkwidget.h:
#include <gtk/gtkwindow.h>
#include < gtk/gtkwidget.h>
...
gtk_window_set_default_size(window1, 400, 400);
gtk_wigdet_set_uposition(window1, 30, 50);

GTK,
.

32

32.1.
32.1.1.
,
gtk_signal_connect():
gint gtk_signal_connect (GtkObject *object,
gchar *name,
GtkSignalFunc func,
gpointer func_data)

:
object , ;
name ;
func , ;
func_data , .


. , , .
, . .
gtk_signal_connect(),
, .
, ,
. ,
button_press_event, . "",
.
: , .

32.

355

- . ( GTK, ):
GtkWidget *widget , ;
gpointer data , . . -

gtk_signal_connect().
, , :
GtkWidget *widget ;
GdkEvent *event ;
gpointer data .

:
button_press_event ;
button_release_event ;
motion_notify_event ;
delete_event ;
destroy_event ;
key_press_event ;
key_release_event ;
enter_notify_event ;
leave_notify_event ;
focus_in_event ( );
focus_out_event ;
drag_begin_event ;
drag_request_event ;
drag_end_event ;
drop_enter_event .

(event) :
GDK_NOTHING ;
GDK_DELETE ;
GDK_DESTROY ;
GDK_MOTION_NOTIFY ;
GDK_BUTTON_PRESS ;
GDK_1BUTTON_PRESS ;
GDK_2BUTTON_PRESS ;

VII. GTK+

356

GDK_3BUTTON_PRESS ;
GDK_BUTTON_RELEASE () ;
GDK_KEY_PRESS ;
GDK_KEY_RELEASE ;
GDK_ENTER_NOTIFY ();
GDK_LEAVE_NOTIFY ;
GDK_FOCUS_CHANGE ;
GDK_OTHER_EVENT .

32.1.2. EventBox
. , (GtkLabel),
(GtkTable), (GtkHBox, GtkVBox) .
, EventBox.
, .
EventBox . 32.1, EventBox button_press_
event GtkLabel.
32.1. EventBox
#include <gtk/gtk.h>
int main( int argc, char *argv[] )
{
GtkWidget *window1;
GtkWidget *event_box1;
GtkWidget *label;

//
// eventbox
//

/* GTK */
gtk_init( &argc, &argv );
/* */
window1 = gtk_window_new( GTK_WINDOW_TOPLEVEL );
gtk_window_set_title( GTK_WINDOW( window1 ), "My App Title" );
/* */
gtk_signal_connect(GTK_OBJECT(window1), "destroy",
GTK_SIGNAL_FUNC(gtk_exit), NULL );
/* */
gtk_container_set_border_width(GTK_CONTAINER(window1), 10);
/* event_box */
event_box1 = gtk_event_box_new();

32.

357

/* event_box */
gtk_container_add( GTK_CONTAINER( window1 ), event_box1 );
/* event_box */
gtk_widget_show( event_box1);
/* */
label = gtk_label_new( "My Label" );
/* event_box */
gtk_container_add(GTK_CONTAINER( event_box1 ), label);
/* */
gtk_widget_show(label);
/* GtkLabel ( ) */
gtk_widget_set_events(event_box1, GDK_BUTTON_PRESS_MASK );
gtk_signal_connect( GTK_OBJECT( event_box1 ), "button_press_event",
GTK_SIGNAL_FUNC( gtk_exit ), NULL );
gtk_widget_realize(event_box1);
/* */
gdk_window_set_cursor( event_box1->window, gdk_cursor_new(GDK_HAND1));
/* */
gtk_widget_show(window1);
gtk_main();
return 0;
}

,
: ,
. ,
. . 32.1.
32.1. GDK

GDK_X_CURSOR
GDK_ARROW
GDK_BASED_ARROW_DOWN

VII. GTK+

358

32.1 ()

GDK_BASED_ARROW_UP
GDK_BOAT
GDK_BOGOSITY
GDK_BOTTOM_LEFT_CORNER
GDK_BOTTOM_RIGHT_CORNER
GDK_BOTTOM_SIDE
GDK_BOTTOM_TEE
GDK_BOX_SPIRAL
GDK_CENTER_PTR
GDK_CIRCLE
GDK_CLOCK
GDK_COFFEE_MUG
GDK_CROSS
GDK_CROSS_REVERSE
GDK_CROSSHAIR
GDK_DIAMOND_CROSS
GDK_DOT
GDK_DOTBOX
GDK_DOUBLE_ARROW
GDK_DRAFT_LARGE
GDK_DRAFT_SMALL
GDK_DRAPED_BOX
GDK_EXCHANGE
GDK_FLEUR
GDK_GOBBLER
GDK_GUMBY
GDK_HAND1
GDK_HAND2
GDK_HEART
GDK_ICON

32.

359
32.1 ()


GDK_IRON_CROSS
GDK_LEFT_PTR
GDK_LEFT_SIDE
GDK_LEFT_TEE
GDK_LEFTBUTTON
GDK_LL_ANGLE
GDK_LR_ANGLE
GDK_MAN
GDK_MIDDLEBUTTON
GDK_MOUSE
GDK_PENCIL
GDK_PIRATE
GDK_PLUS
GDK_QUESTION_ARROW
GDK_RIGHT_PTR
GDK_RIGHT_SIDE
GDK_RIGHT_TEE
GDK_RIGHTBUTTON
GDK_RTL_LOGO
GDK_SAILBOAT
GDK_SB_DOWN_ARROW
GDK_SB_H_DOUBLE_ARROW
GDK_SB_LEFT_ARROW
GDK_SB_RIGHT_ARROW
GDK_SB_UP_ARROW
GDK_SB_V_DOUBLE_ARROW
GDK_SHUTTLE
GDK_SIZING
GDK_SPIDER
GDK_SPRAYCAN

VII. GTK+

360

32.1 ()

GDK_STAR
GDK_TARGET
GDK_TCROSS
GDK_TOP_LEFT_ARROW
GDK_TOP_LEFT_CORNER
GDK_TOP_RIGHT_CORNER
GDK_TOP_SIDE
GDK_TOP_TEE
GDK_TREK
GDK_UL_ANGLE
GDK_UMBRELLA
GDK_UR_ANGLE
GDK_WATCH
GDK_XTERM

32.2. GTK
, , ,
. ,
.
, (
) .
.
, :
include <locale.h>
...
setlocale(LC_ALL, "ru_RU.UTF-8");

UTF-8,
( locale.h). KOI8-R:
setlocale(LC_ALL, "ru_RU.KOI8-R");

32.

361

. 32.1 . , . setlocale(). setlocale()


gtk_init():
GtkWidget *window1;
setlocale(LC_ALL, "ru_RU.UTF-8");
gtk_init( &argc, &argv );

. 32.1.

32.3.
, , . .
( destroy) .

gtk_widget_destroy(), gtk/gtkwidget.h:
void gtk_widget_destroy (GtkWidget *widget);

, .
GTK gtk_container_
remove(), :
void gtk_container_remove(GtkContainer *cont, GtkWidget *w);

:
. ,
. ( , ), g_object_ref(), .
label cont1 cont2:

362

VII. GTK+

g_object_ref(GTK_WIDGET(label));
gtk_container_remove(GTK_CONTAINER(cont1), label);
gtk_container_add(GTK_CONTAINER(cont2), label);

, .
,
gtk_widget_destroy().
gtk_widget_hide(), gtk_widget_show():
void gtk_widget_hide(GtkWidget *w);
void gtk_widget_show(GtkWidget *w);

:
GTK_STATE_NORMAL ;
GTK_STATE_ACTIVE (, );
GTK_STATE_PRELIGTH ;
GTK_STATE_SELECTED ( );
GTK_STATE_INSENSITIVE ().

:
GTK_WIDGET(w)->state

GTK_WIDGET_STATE(widget), gtk/gtkwidget.h.
gtk_widget_set_sensitive():
gtk_widget_set_sensitive(widget, FALSE);

.
FALSE, , TRUE .
,
gtk_widget_grab_focus():
gtk_widget_grab_focus(GtkWidget *w);

32.4. ,
, . ,
. , .
. . . GtkBin. GtkContainer.
, : , , .

32.

363

. :
GtkHBox ;
GtkVBox ;
GtkFixed ;
GtkTable .

GtkTable, . ,
, .
, GtkTable , .
. , /etc/resolv.conf.
:
search _
nameserver IP__DNS-
nameserver IP__DNS-

search , , . ,
"com net ru".
http://mail, ( . resolver , ) mail.com,
,
mail.net . .
nameserver IP- DNS-, . IP-
( ), resolv.conf
nameserver. nameserver
IP-.

/etc/resolv.conf root. , , auth
, , .
resolv.conf,
, /etc. ,
(, ) ,
root, . .
. 32.2 . . - <Enter>, -

VII. GTK+

364

. Ok, .
Quit . Ok
, . gtk_main_quit()
Ok.

. 32.2. resolver.c

,
. :
GtkWidget *edit[3];

gtk_entry_new():
edit[i] = gtk_entry_new();

gtk_entry_set_editable(), .
gtk_entry_set_editable(GTK_ENTRY(edit[i]), 1);

<Enter> :
gtk_signal_connect(GTK_OBJECT(edit[i]), "activate",
GTK_SIGNAL_FUNC(enter_callback), edit[i]);

, <Enter>
, , <Enter> .

32.

365

<Enter> enter_callback(),
. .
, . . . :
domain = gtk_entry_get_text(GTK_ENTRY(edit[0]));
dns1 = gtk_entry_get_text(GTK_ENTRY(edit[1]));
dns2 = gtk_entry_get_text(GTK_ENTRY(edit[2]));

Ok
resolv.conf, :
/* resolv.conf */
if ((resolv = fopen("resolv.conf","w")) == NULL)
{
/* , ... */
g_print ("ERR: Cannot to open resolve.conf file\n");
gtk_main_quit ();
}
/* */
fprintf(resolv,"domain %s\n", domain);
fprintf(resolv,"nameserver %s\n", dns1);
fprintf(resolv,"nameserver %s\n", dns2);
fclose(resolv);

. , . , .
: ,
EventBox. ,
. : , , ,
, . .
:
label = gtk_label_new("Domain: ");
gtk_table_attach_defaults (GTK_TABLE(table), label, 0, 1, 0, 1);
gtk_widget_show (label);
label = gtk_label_new("DNS #1: ");
gtk_table_attach_defaults (GTK_TABLE(table), label, 0, 1, 1, 2);
gtk_widget_show (label);
label = gtk_label_new("DNS #2: ");
gtk_table_attach_defaults (GTK_TABLE(table), label, 0, 1, 2, 3);
gtk_widget_show (label);

( button) GTK (), . 32.2.

VII. GTK+

366

32.2.

clicked

pressed

( )

released

enter

leave

resolver ( 32.2). , GtkTable.


32.2. resolver.c
#include <gtk/gtk.h>
#include <stdlib.h>
#include <stdio.h>
/* , IP- DNS- */
gchar *domain, *dns1, *dns2;
/* .
, [1] [2] IP- DNS*/
GtkWidget *edit[3];
/* */
FILE *resolv;
/* , Ok */
void writetofile( GtkWidget *widget,
gpointer
data )
{
/* gtk_entry_get_text()
*/
domain = gtk_entry_get_text(GTK_ENTRY(edit[0]));
dns1 = gtk_entry_get_text(GTK_ENTRY(edit[1]));
dns2 = gtk_entry_get_text(GTK_ENTRY(edit[2]));
/* */
g_print ("Domain %s\n", domain);
g_print ("DNS1 %s\n", dns1);
g_print ("DNS2 %s\n", dns2);

32.

367

/* resolv.conf */
if ((resolv = fopen("resolv.conf","w")) == NULL)
{
/* ... */
g_print ("ERR: Cannot to open resolve.conf file\n");
gtk_main_quit ();
}
/*
domain
search, Domain
*/
fprintf(resolv,"search %s\n",domain);
fprintf(resolv,"nameserver %s\n",dns1);
fprintf(resolv,"nameserver %s\n",dns2);
fclose(resolv);
}
/* Quit */
gint delete_event( GtkWidget *widget,
GdkEvent *event,
gpointer
data )
{
/* gtk_main_quit()
GTK-. exit()
stdlib.h */
gtk_main_quit ();
return(FALSE);
}
/* <Enter> */
void enter_callback( GtkWidget *widget,
GtkWidget *entry )
{
domain = gtk_entry_get_text(GTK_ENTRY(entry));
printf("Text: %s\n", domain);
}

int main( int


argc,
char *argv[] )
{
GtkWidget
GtkWidget
GtkWidget
GtkWidget

*window;
*button;
*table;
*label;

/*
/*
/*
/*

*/
*/
*/
*/

VII. GTK+

368
gint i;

/* */

/* GTK- */
gtk_init (&argc, &argv);
/* */
window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
/* */
gtk_window_set_title (GTK_WINDOW (window), "Resolver");
/* . delete_event
: delete_event(),
*/
gtk_signal_connect (GTK_OBJECT (window), "delete_event",
GTK_SIGNAL_FUNC (delete_event), NULL);
/* */
gtk_container_set_border_width (GTK_CONTAINER (window), 20);
/* 3x3 */
table = gtk_table_new (3, 3, TRUE);
/* . ! */
gtk_container_add (GTK_CONTAINER (window), table);
/* , .

*/
label = gtk_label_new("Domain: ");
/* */
gtk_table_attach_defaults (GTK_TABLE(table), label, 0, 1, 0, 1);
gtk_widget_show (label);
label = gtk_label_new("DNS #1: ");
gtk_table_attach_defaults (GTK_TABLE(table), label, 0, 1, 1, 2);
gtk_widget_show (label);
label = gtk_label_new("DNS #2: ");
gtk_table_attach_defaults (GTK_TABLE(table), label, 0, 1, 2, 3);
gtk_widget_show (label);
/* */
for(i=0; i<3; i++)

32.

369

{
/* */
edit[i] = gtk_entry_new();
gtk_entry_set_editable(GTK_ENTRY(edit[i]), 1);
/* activate
<Enter>*/
gtk_signal_connect(GTK_OBJECT(edit[i]), "activate",
GTK_SIGNAL_FUNC(enter_callback),
edit[i]);
/* edit[i] */
gtk_table_attach_defaults (GTK_TABLE(table), edit[i],
1, 2, i, i+1);
/* */
gtk_widget_show (edit[i]);
}
/* Ok, ,
*/
button = gtk_button_new_with_label ("Ok");
gtk_table_attach_defaults (GTK_TABLE(table), button, 2, 3, 0, 1);
gtk_signal_connect(GTK_OBJECT(button),"clicked",
GTK_SIGNAL_FUNC(writetofile), NULL);
gtk_widget_show (button);
/* Quit */
button = gtk_button_new_with_label ("Quit");
gtk_table_attach_defaults (GTK_TABLE(table), button, 2, 3, 2, 3);
gtk_signal_connect(GTK_OBJECT(button),"clicked",
GTK_SIGNAL_FUNC(delete_event), NULL);
gtk_widget_show (button);
gtk_widget_show (table);
gtk_widget_show (window);

/* */
/* */

/* GTK- */
gtk_main ();
return 0;
}

, .
GtkTable. 33, . , . :
table = gtk_table_new (3, 3, TRUE);

VII. GTK+

370

.
Excel: .
:
gtk_table_attach_defaults (GTK_TABLE(table), button, 2, 3, 0, 1);

X, Y. (X)
Ok , 2 3. (Y)
0 1. :
0
1
Domain 1

1
DNS1
2
2
DNS2
3
3

Quit

, . -
, Glade.

32.5.

, : (radio buttons)
(check buttons). ,
, (. . 32.2).
:
GtkWidget *gtk_check_button_new( void );
GtkWidget *gtk_check_button_new_with_label ( gchar *label );

( ), , , ,
. , , . , , , . .
gtk_check_button_new_with_label(). ,
, .

:
GtkWidget *gtk_radio_button_new( GSList *group );
GtkWidget *gtk_radio_button_new_with_label( GSList *group, ghar *label );

32.

371

group .
.
:
GSList *gtk_radio_button_group( GtkRadioButton *radio_button );

, :
button2 = gtk_radio_button_new_with_label(
gtk_radio_button_group (GTK_RADIO_BUTTON (button1)),
"button2");

gtk_toggle_button_set_active() :
void gtk_toggle_button_set_active( GtkToggleButton *toggle_button, gint state );

: gtk_toggle_button_set_active()
toggle-. ,
: . ,
gtk_toggle_button_set_active(). ,
. ( ) toggle- :
http://www.gtk.org/tutorial1.2/gtk_tut-6.html
, , ,
, . . , .
:
1. clicked -
clicked . ,
- .
, . . .
2. gtk_toggle_button_get_active()
toggle-, , ( , check button radio button).
/ . gtk_toggle_button_get_active() , . . ,
. ,
, , .

VII. GTK+

372

:
if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(button1)))
g_print(" button1 \n");

: gtk_toggle_button_get_active() ,
( ) GTK_TOGGLE_BUTTON.

( 32.3). GtkVBox. .
( )
OK. "" ,
. , , .
32.3.
#include <gtk/gtk.h>
#include <glib.h>
#include <locale.h>
/* ,
close_applicaion */
GtkWidget *button1;
GtkWidget *button2;
/* , ,
*/
gint close_application( GtkWidget *widget,
GdkEvent *event,
gpointer
data )
{
if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(button1)))
g_print("Fedora \n");
if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(button2)))
g_print("Denix \n");
gtk_main_quit();

/* */

return(FALSE);
}
int main( int
argc,
char *argv[] )

32.
{
/* , , */
GtkWidget *window = NULL;
GtkWidget *box1;
GtkWidget *box2;
GtkWidget *separator;
GtkWidget *button;
/* */
GSList *group;
/* */
setlocale(LC_ALL, "ru_RU.UTF-8");
gtk_init(&argc,&argv);
window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
/* */
gtk_signal_connect (GTK_OBJECT (window), "delete_event",
GTK_SIGNAL_FUNC(close_application), NULL);
/* */
gtk_window_set_title (GTK_WINDOW (window), " ");
/* */
gtk_container_set_border_width (GTK_CONTAINER (window), 0);
/* */
box1 = gtk_vbox_new (FALSE, 0);
gtk_container_add (GTK_CONTAINER (window), box1);
/* */
gtk_widget_show (box1);
/* */
box2 = gtk_vbox_new (FALSE, 10);
gtk_container_set_border_width (GTK_CONTAINER (box2), 10);
gtk_box_pack_start (GTK_BOX (box1), box2, TRUE, TRUE, 0);
gtk_widget_show (box2);
/* */
button1 = gtk_radio_button_new_with_label (NULL, "Fedora");
gtk_box_pack_start (GTK_BOX (box2), button1, TRUE, TRUE, 0);
gtk_widget_show (button1);
/* */
/* */
group = gtk_radio_button_group (GTK_RADIO_BUTTON (button1));

373

VII. GTK+

374

. 32.3.

/* */
button2 = gtk_radio_button_new_with_label(group, "Denix");
gtk_box_pack_start (GTK_BOX (box2), button2, TRUE, TRUE, 0);
gtk_widget_show (button2);
/* */
separator = gtk_hseparator_new();
gtk_box_pack_start (GTK_BOX (box1), separator, FALSE, TRUE, 0);
gtk_widget_show (separator);
/* ,
GtkTable
*/
box2 = gtk_vbox_new (FALSE, 10);
gtk_container_set_border_width (GTK_CONTAINER (box2), 10);
gtk_box_pack_start (GTK_BOX (box1), box2, FALSE, TRUE, 0);
gtk_widget_show (box2);
/* K close_application */
button = gtk_button_new_with_label ("OK");
gtk_signal_connect_object (GTK_OBJECT (button), "clicked",
GTK_SIGNAL_FUNC(close_application),
GTK_OBJECT (window));
gtk_box_pack_start (GTK_BOX (box2), button, TRUE, TRUE, 0);
GTK_WIDGET_SET_FLAGS (button, GTK_CAN_DEFAULT);

32.

375

gtk_widget_grab_default (button);
gtk_widget_show (button);
gtk_widget_show (window);
gtk_main();
return(0);
}

. 32.3.

32.6. CList
CList , . . . :
GtkWidget *gtk_clist_new ( gint columns );
GtkWidget *gtk_clist_new_with_titles( gint columns, gchar *titles[] );

, . columns .
:
gint gtk_clist_prepend( GtkCList *clist, gchar *text[] );
gint gtk_clist_append( GtkCList *clist, gchar *text[] );

, .
, :
void gtk_clist_insert( GtkCList *clist,
gint row, gchar *text[]);

row.
0.
:
void gtk_clist_remove( GtkCList *clist, gint row );
void gtk_clist_clear( GtkCList *clist );

row, .
32.4, CList.
,
. .
, . / .
. 32.4.

VII. GTK+

376

. 32.4. cslist.c

32.4. CList (cslist.c)


#include <gtk/gtk.h>
#include <locale.h>
/* "", */
void button_add_clicked( gpointer data )
{
int indx;
/* */
gchar *dist[4][2] = {

{
{
{
{

"1",
"2",
"3",
"4",

"Fedora" },
"Mandriva Linux" },
"openSUSE" },
"Denix" } };

for ( indx=0 ; indx < 4 ; indx++ )


gtk_clist_append( (GtkCList *) data, dist[indx]);
return;
}
/* "" */
void button_clear_clicked( gpointer data )
{
/* */
gtk_clist_clear( (GtkCList *) data);
return;
}
/* / */
void button_hide_show_clicked( gpointer data )

32.

377

{
/* 0 =
static short int flag = 0;

*/

if (flag == 0)
{
/* */
gtk_clist_column_titles_hide((GtkCList *) data);
flag++;
}
else
{
/* */
gtk_clist_column_titles_show((GtkCList *) data);
flag--;
}
return;
}
/* , */
void selection_made( GtkWidget
*clist,
gint
row,
gint
column,
GdkEventButton *event,
gpointer
data )
{
gchar *text;
/* ( ) */
gtk_clist_get_text(GTK_CLIST(clist), row, column, &text);
/* */
g_print(" %d. %d, %s\n\n",
row, column, text);
return;
}
int main( int
argc,
gchar *argv[] )
{
GtkWidget *window;
GtkWidget *vbox, *hbox;
GtkWidget *scrolled_window, *clist;
GtkWidget *button_add, *button_clear, *button_hide_show;

VII. GTK+

378
/* */
gchar *titles[2] = { "", "" };
setlocale( LC_ALL, "ru_RU.UTF-8");
gtk_init(&argc, &argv);

window=gtk_window_new(GTK_WINDOW_TOPLEVEL);
gtk_widget_set_usize(GTK_WIDGET(window), 300, 150);
gtk_window_set_title(GTK_WINDOW(window), "");
gtk_signal_connect(GTK_OBJECT(window),
"destroy",
GTK_SIGNAL_FUNC(gtk_main_quit),
NULL);
vbox=gtk_vbox_new(FALSE, 5);
gtk_container_set_border_width(GTK_CONTAINER(vbox), 5);
gtk_container_add(GTK_CONTAINER(window), vbox);
gtk_widget_show(vbox);
/* */
scrolled_window = gtk_scrolled_window_new (NULL, NULL);
gtk_scrolled_window_set_policy (
GTK_SCROLLED_WINDOW(scrolled_window),
GTK_POLICY_AUTOMATIC,
GTK_POLICY_ALWAYS);
gtk_box_pack_start(GTK_BOX(vbox), scrolled_window, TRUE, TRUE, 0);
gtk_widget_show (scrolled_window);
/* */
clist = gtk_clist_new_with_titles( 2, titles);
/* */
gtk_signal_connect(GTK_OBJECT(clist), "select_row",
GTK_SIGNAL_FUNC(selection_made),
NULL);
/* */
gtk_clist_set_shadow_type (GTK_CLIST(clist), GTK_SHADOW_OUT);
/* . 0 */
gtk_clist_set_column_width (GTK_CLIST(clist), 0, 150);
/* */
gtk_container_add(GTK_CONTAINER(scrolled_window), clist);
gtk_widget_show(clist);

32.

379

/* "", "",
"/" */
hbox = gtk_hbox_new(FALSE, 0);
gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, TRUE, 0);
gtk_widget_show(hbox);
button_add = gtk_button_new_with_label("");
button_clear = gtk_button_new_with_label("");
button_hide_show = gtk_button_new_with_label("/");
gtk_box_pack_start(GTK_BOX(hbox), button_add, TRUE, TRUE, 0);
gtk_box_pack_start(GTK_BOX(hbox), button_clear, TRUE, TRUE, 0);
gtk_box_pack_start(GTK_BOX(hbox), button_hide_show, TRUE, TRUE, 0);
/* */
gtk_signal_connect_object(GTK_OBJECT(button_add), "clicked",
GTK_SIGNAL_FUNC(button_add_clicked),
(gpointer) clist);
gtk_signal_connect_object(GTK_OBJECT(button_clear), "clicked",
GTK_SIGNAL_FUNC(button_clear_clicked),
(gpointer) clist);
gtk_signal_connect_object(GTK_OBJECT(button_hide_show), "clicked",
GTK_SIGNAL_FUNC(button_hide_show_clicked),
(gpointer) clist);
gtk_widget_show(button_add);
gtk_widget_show(button_clear);
gtk_widget_show(button_hide_show);
gtk_widget_show(window);
gtk_main();
return(0);
}

32.7.
. , , . .
, , OK . OK
, . ,
. 32.5.

VII. GTK+

380

. 32.5.

32.9.
#include <gtk/gtk.h>
#include <locale.h>
/* */
void file_ok_sel( GtkWidget *w, GtkFileSelection *fs )
{
g_print ("%s\n",
gtk_file_selection_get_filename (GTK_FILE_SELECTION (fs)));
}
void destroy( GtkWidget *widget, gpointer
{
gtk_main_quit();
}
int main( int
argc,
char *argv[] )
{
GtkWidget *file_dial;

data )

32.

381

setlocale( LC_ALL, "ru_RU.UTF-8");


gtk_init (&argc, &argv);
/* */
file_dial = gtk_file_selection_new (" ");
gtk_signal_connect (GTK_OBJECT (file_dial), "destroy",
(GtkSignalFunc) destroy, &file_dial);
/* OK "" */
gtk_signal_connect (GTK_OBJECT
(GTK_FILE_SELECTION (file_dial)->ok_button),
"clicked", (GtkSignalFunc) file_ok_sel, file_dial );
gtk_signal_connect_object (GTK_OBJECT (
GTK_FILE_SELECTION(file_dial)->cancel_button),
"clicked",
(GtkSignalFunc) gtk_widget_destroy,
GTK_OBJECT (file_dial));
/* */
gtk_file_selection_set_filename (GTK_FILE_SELECTION(file_dial),
"photo.jpg");
gtk_widget_show(file_dial);
gtk_main();
return 0;
}

32.8.

GTK. , , . .
. Glade. ""
, , GtkTable
, . :
, .
Glade ,
. , .
, Glade , .

33

Glade
33.1.
,
Linux, Windows. ( ) , (RAD, Rapid
Application Development). Microsoft Visual
Studio, Borland Delphi, Lazarus .
RAD- . , . , "", , , , , . .
Linux : QtDevelop (
, Qt), Lazarus ( , Delphi
Linux) Glade UI Builder ( GTK-).
QtDevelop ( QtDesigner) RAD-,
, (. . ).
Lazarus, Pascal ( Free
Pascal), QtDevelop, C++.
Glade UI Builder, RAD- . Glade , , . . ,
, Glade .
( C C++)
, , gdb. Glade
, ,
Glade. Glade .

33. Glade

383

Glade :
1. , .
Glade. "" .glade,
.
XML,
gedit .
2. C C++. Glade . , .
3. , Makefile .
4. make.
RAD- ,
Glade - .

33.2. Glade
Glade ,
glade3, glade-gnome

. 33.1. libgtk+2.0._0-devel

VII. GTK+

384

glade. glade .
, C++, ,
libgtk+2.0._0-devel ( libgtk2.0-dev) gcc-c++ ( C++) . 33.1.

33.3. Glade
Glade . ,
. , , (), , . .
,
, .
:
, .
Glade. Glade
(. 33.2). Glade.
, (

. 33.2.

33. Glade

385

), : , .
(
, )
. 33.3.

. 33.3.

. , , ,
. ,
(. 33.4).
( button) ( ).
:
(window1), (table1) (button1).
, . (. 33.5).
Glade , - .

VII. GTK+

386

. 33.4.

. 33.5. button

33. Glade

387

clicked .
, on_button1_clicked,
(. 33.6). ,
gtk_main_quit(), .
- ,
, gtk_main_quit()
, .
, gtk_main_quit().

. 33.6. clicked

destroy ,
(, - ,
- "" ).
window1, gtk_main_quit()
destroy (. 33.7).
first-glade 33.1, , , .

VII. GTK+

388

, , . ,
.
.

. 33.7. destroy

33.4.
C, C++ ( ,
, , ).
C++, ,
. 33.1
, , Glade.
33.1. first-glade.c
#include <gtk/gtk.h>
// : locale.h ,
// setlocale
//
// Glade
#define UI_FILE "first-glade.glade"
//
GtkBuilder *builder;
// "" ,
GtkWidget *window1;
//
GtkWidget *button1;
//
//
//
extern "C" void on_button1_clicked (GtkObject *object,
gpointer user_data);

33. Glade
// !
int main( int argc, char **argv )
{
GError *error = NULL;
// GTK+
gtk_init( &argc, &argv );
// GtkBuilder
builder = gtk_builder_new();
//
if( ! gtk_builder_add_from_file( builder, UI_FILE, &error ) )
{
g_warning( "%s", error->message );
g_free( error );
return( 1 );
}
//
// ,
// gtk_builder_get_object
// , Glade
window1 = GTK_WIDGET(gtk_builder_get_object(builder, "window1"));
button1 = GTK_WIDGET(gtk_builder_get_object(builder, "button1"));
//
gtk_builder_connect_signals (builder, NULL);
//
g_object_unref( G_OBJECT( builder ) );
//
gtk_widget_show(window1);
//
gtk_main();
return( 0 );
}
void on_button1_clicked (GtkObject *object, gpointer user_data)
{
// GTK-
gtk_main_quit();
}

389

VII. GTK+

390

, Glade ,
, .
, .

33.5.
GTK-, , Makefile
. Makefile first-glade 33.2.
33.2. Makefile
CC=g++
LDLIBS=`pkg-config --libs gtk+-2.0 gmodule-2.0`
CFLAGS=-Wall -g `pkg-config --cflags gtk+-2.0 gmodule-2.0`
first-glade: first-glade.o
$(CC) $(LDLIBS) first-glade.o -o first-glade
first-glade.o: first-glade.c
$(CC) $(CFLAGS) -c first-glade.c
clean:
rm -f first-glade
rm -f *.o

:
make

33.6.
, ,
GTK+.
, ,
GTK.
, "" GTK, :
http://developer.gnome.org/gtk/
GTK 2.24 2.22,
. , , GTK:
http://www.opennet.ru/docs/RUS/gtk-reference/

33. Glade

391

2.10,
.
http://www.gtk.org/, GLib, GTK, GDK, GTK Windows OSX.
Glade ( )
:
http://habrahabr.ru/blogs/development/107403/
Glade ,
, <F1>
, .

392

VII. GTK+

VIII


34.

35.


gdb gprof.

34

.

34.1.
, . . ,
. .
? , ,
, : , "" (runtime error).
, .
: ( ),
, - . .
. : , . , ,
.
. ,
. . : .
, , .
, . , (
).
,
.

34. .

395


, :
a = b++ + 10;
a = ++b + 10;

x 10 ( ,
b = 1), 11. , 1 ,
. , , , ,
.

. , . , 100 ,
:
for (i=0;i<=100;i++) a[i] = 0;

, , 100,
0 99.
,
0,
1 100:
for (i=1;i<=100;i++) a[i] = 0;

, , .
C/C++ ,
, . C , . -
.
"" * &,
.
. , .
- , .
( ) , , .
. Linux
"" gdb (The GNU Debugger),
. gdb
Linux ( , ,
gdb).

VIII.

396

:
-

,
. (, , ),
, ;
(breakpoint) -

. , .
, .
, . ,
;
,

.
, gdb.

34.2. gdb
gdb ,
. 34.1. gdb :
gdb [-help] [-nx] [-q] [-batch] [-cd=dir] [-f] [-b bps] [-tty=dev] [-s symfile]
[-e prog] [-se prog] [-c core] [-x cmds] [-d dir] [prog[core|procID]]
34.1. gdb

-help h

-nx n


.gdbinit

-q

-batch

. 0, , ,
x ( .gdbinit, ).

-cd=

(
)

34. .

397
34.1 ()

-f fullname

,
Emacs
gdb. . Emacs ,

-b bps (bits per second)

-tty=


.
: ,

-s symbols=

-write

core-

-e

-se=

-core= -c

core- ( )

-command= -x

, ,
( )

-d

[prog|core|procID]

.
(prog), - (core)
(procID)

,
-g, :
gcc g o prog prog.c

:
gdb prog

(core), :
gdb prog core

PID :
gdb 1234

:
.
. 34.2.

VIII.

398

34.2.

break [:]
break [:]

.
, ,
,
, ,

run []

bt

print

, , .

( )

kill

list

next

.
. ""
,

step

. next ,
,
, , .
,
C, C -g

help []

quit

watch []

"" : , .
watch next/step, watch .
awatch

awatch []

, ( ) . awatch
watch

, . 34.2 , , ,
.
help.

34. .

399

34.3. gdb
gdb.
.
* C ( 34.1).
34.1. error.c
#include <stdio.h>
int main()
{
char *name = "Denis";
*name = 'A';
return 0;
}

. 34.1: nano error.c,


( -g) . , .

. 34.1.

VIII.

400

:
gdb error


, gdb error option1 option2.

, (. 34.2).

. 34.2. ,

run. , , (. 34.3).

, , , , . .
:
break main

main
, . , . . main
,
.

( )
, c.

run , (. 34.4).

34. .

. 34.3.

. 34.4.

401

402

VIII.

. 34.5. awatch

. 34.6. step

34. .

403

name, ,
name .
. 34.5. (
awatch) name step . awatch
name. ,
awatch, step (. 34.6).

. 34.7. DDD

gdb,
gdb. gdb
, DDD.
,
(. 34.7).

404

VIII.

34.4.
, , , , ,
.
strace, , . ,
, .
strace :
strace [ -dffhiqrtttTvxx ] [ -acolumn ] [ -eexpr ] ... [ -ofile ] [ -ppid ] ...
[ -sstrsize ] [ -uusername ] [ command [ arg ... ] ]

strace .
- .
:
strace error

. 34.8 , , ?

. 34.8. strace

34. .

405

strace :
=

:
open("/lib/libc.so.6/ O_RDONLY) = 3

:
--- SIGINT (Interrupt) --+++ killed by SIGINT +++

, "" SIGSEGV
(Segmentation fault).
strace
. 34.3.
34.3. strace

, .

-d

strace

-f

-ff

_.pid.
o
_

-F

vfork().
f

-h

-i

-q

-r

-t

-tt

, t,

-T

, (. .
)

-v

-V

strace

-x

-ASCII

-xx

( !)

VIII.

406

34.3 ()

-a


( 40)

-e trace=

. ,
trace=open,close,read,write

-e trace=file

(open,
close, stat, chmod, unlink . .)

-e trace=process

(fork, exec, wait


.)

-e trace=network

-e trace=signal

-e trace=ipc

IPC- ( )

-e abbrev=

. ,
abbrev=all abbrev=none

-e verbose=

,
verbose=all

-e raw=set

.
,

-e signal=

.
signal=all. , signal=!SIGTERM , SIGTERM

-e read=

ASCII-
read() . ,
, 2 7, read=2,7

-e write=

, -e read,

-o _

-p pid

PID=pid

-s

( 32).

-S

, c,
: time (), calls (), name ()
nothing ( )

-u _

.
,

35


35.1.
gprof
, . , , . ,
. , . . gprof. , openSUSE
gprof, gcc. .
gprof (The GNU Profiler),
.
. 35.1.
35.1. gprof

-a

-b

-c

-e _

-E _

-f _

-F _

-k func1 func2

func2 func1

VIII.

408

35.1 ()

-s

gmon.sum

-T

BSD-, ,
BSD

-Q ( --no-graph)

-w

""

-z

gprof man gprof.

35.2.

pg. , :
gmon.out: no such file or directory

o, , . .
a.out.
a.out,
gmon.out. --nograph:
$ gcc pg demo.c
$ ./a.out
$ gprof --no-graph

--no-graph ( -Q)
. 35.1.
, b. (. 35.2)
, -b.
-b . 35.2.
35.2.

time

cumulative seconds

,
( )

35.

409
35.2 ()

self seconds

calls

self ms/calls

total ms/calls

,
,

name

, function function2,
demo.c ( 35.1).

. 35.1. gprof ( )

VIII.

410

. 35.2. gprof -b

35.1. demo.c
#include <stdio.h>
int function2()
{
int i;
// ,
for (i=0; i<9999999; i++) ;
return 111;
}
int function()
{
int i;
double x = 7.7723232323;
double y = 524543.5454;

35.

411

//
// x y,
//
for (i=0; i<9999999; i++) x/y;
// function2()
function2();
return x/y;
}
int main()
{
int i;
double k;
for (i=0; i<10; i++)
{
printf("%d\b", i);
k = function();
}
return 0;
}

(. . 35.1). 35.1,
function() 10 (. calls).
function2(), , 10.
function() 0,25 (self seconds),
function2(), cumulative seconds 0,58
(0,25 + 0,33). . 35.2 function(). 0,25 , (children)
0,33 .
function2() 0,33 , ,
cumulative seconds 0,33 .
(self), (children)
0.
, , ,
printf(), 10 , function().
, libc.so
-pg,
.
, ,
, ,
- .
, , ,
, .

412

VIII.

, . , ,
. . ,
, ,
. , . ,
-O. , ,
. , , .
, . , "" .


Linux , ,

.
: , man.
:
. /usr/share
, TCL/Tk GTK.
, Linux. , Qt, ,
KDE. Qt :
. ,
QtDesigner, . , ,
Qt:
. Qt4.5. C++
(http://bhv.ru/books/book.php?id=186572)

GTK, Qt C/C++ Linux.


- , , ( )
:
http://www.dkws.org.ua/phpbb2/viewtopic.php?t=5005
Genie Vala:
Python' , C#.
Python? Genie ,
Python, ,
"" , -

414

.
:
http://bkhome.org/genie/index.html
Pascal Free Pascal
Compiler (FPC) Lazarus,
Borland Delphi.
MonoDevelop,
C#:
http://monodevelop.com/Download
,
,
, :
http://www.dkws.org.ua

Linux
Linux, ,
.
.
, . Linux- . ? , . , ,
.
, . ,
.
Mandriva 2010 ,
.
"" www.kernel.org. , ,
, www.kernel.org.

1.

drakrpm |
kernel-source (. 1). drakrpm (. 2).

416

. 1. kernel-source

. 2.

Linux

417

2.
/usr/src/linux:
# cd /usr/src/linux

:
# make menuconfig
# make xconfig


/ .
menuconfig (. 3) , (
). xconfig .

xconfig Qt, ,
KDE. GNOME,
gconfig, GTK. : menuconfig .

. , , , , .
,
. 1, .

. 3. make menuconfig

418

1.

General setup

, -,
System V, Sysctl. ,
, <F1>.
, !

Enable loadable
module support

. Linux . , .
.
,
" ",
, . ,
,
,

Enable the block


layer

Processor type and


features

Power management
and ACPI options

(ACPI, APM)

Bus options

/ ,

Executable file
formats / Emulations

Networking
support

Device drivers

. , ,

Firmware drivers

( BIOS)

File systems

,
,

Kernel Hacking

Security options

Cryptographic API

( )

Virtualization

Library routines

(
, , CRC)

Unofficial 3rd party


kernel additions

( ).
( )
. , ,
,

Linux

419

, . ,
( ). , .
M. , .
, M,
"" , . ,
. , ,
.
: (. 4)? , !

. 4. ?

3.
, make (. 5), make help.
make .
make help make.
make help, , make ( ) make all, ( *):
vmlinuz , "" ;
modules ;
bzImage , arch/i386/boot.

420

. 5. make

, make
, : # make.

(. 6) . ,
, ,
,
. 12 ( , , ).
( VMware) 5 .

. , . :
# make modules_install

, .
.
:
# make install

(. 7)
. reboot .
custom__, Linux
2.6.31.5-1mnbcustom (. 1.8). , , .

Linux

421

. 6.

. 7. (make install)

422

. 8.


( "" 3 ), make clean
"" . " " root :
# cd /usr/src/linux
# make clean

! .

A
Almquist shell 19
APM 418
ar 73
ash 19
AT&T 16
autoconf 66
automake 66

B
bash 14, 17, 20
binutils 61
breakpoint 396

G
gcc 61
-fPIC 75
gcc-c++ 61
gdb 395
Genie 413
GID 233
Glade 382
gprof 407
GTK+ 338
GTK- 355

H
HTTP 245

C
csh 16

D
dialog 45
DNS 245
DOS 196

E
Entry point 112

F
FIFO 137
File mode 90
FreeBSD 16
FTP 245

I
IMAP 245
init 79
Input/Output 83
IP 243
IPC 123, 133
IPC Key 140
IPng 246
IPv6 246
IP- 245
i- 200

K
kbuild 165
Key loggers 187
klogd 163
ks 16

424

L
Lazarus 382
Login shell 32

M
MAC- 243
make 61, 161
Makefile 66
Mandriva 206
MBR 199
mcedit 60
Monodevelop 414
Multics 109

N
nano 60
NAT 246
NIC 246
nmap 332

O
OSI 242

P
pdksh 17
Permissions 90
PID 100, 120
POP 245
Position Independent Code 75
POSIX 16
PPID 120
proc 234

Q
QtDesigner 382
QtDevelop 382

R
RAD 382

S
Segmentation fault 405
sh 15

SMP 111
SMTP 245
SSL 244
sysctl 142
sysfs 234
syslog 163
syslog-ng 163
System V 140

T
tar 73
TCL 266
TCL-
append 285
array 289
bind 319
button 304
checkbutton 307
concat 284
entry 315
exec 333
expr 275
foreach 288
format 272
gets 274, 293
grid 321
if 276
incr 277
join 288
lappend 284
lindex 284
linsert 285
list 283
listbox 318
lrange 284
lreplace 285
lsearch 285
menu 313
message 329
pack 268, 302
puts 269, 271
radiobutton 311
read 295
seek 296
set 272
spinbox 315
split 287
string 278
tell 296

text 333
tk_getOpenFile 330
tk_getSaveFile 330
tk_mesagebox 328
toplevel 328
while 277
TCP 244
TCP/IP 244
tcsh 18, 31
TENEX 18, 31
THREAD_ID 123
Threads 122
TK 266

U
Ubuntu 31, 208
udev 202

GDK 339
glib 339
Makefile 76
pthread 123
71
71
199

298, 346
35

199

249

202

425

UID 120, 233


UUID 202

V
Vala 413
vi 60
Virtual File System 234

X
Xdialog 57

Z
zsh 17

194

/usr/src/linux/include/linux/msg.h 141
/usr/src/linux/include/linux/sem.h 149
/usr/src/linux/include/linux/shm.h 154
dirent.h 215, 216
fcntl.h 92, 93
glib.h 339
glist.h 342
gslist.h 342
gtimer.h 344
gtk.h 347
gtk/gtkwidget.h 353, 361, 362
gtk/gtkwindow.h 353
kernel.h 162
linux/fs.h 175
linux/init.h 164
linux/ipc.h 143
locale.h 360
mntent.h 226

426

(.)
module.h 162
netinet/in.h 250
proc_fs.h 184
pthread.h 129
pwd.h 121
signal.h 120
socket.h 249
stdarg.h 86
stdio.h 87, 223
stdlib.h 81, 107
strings.h 229
sys/stat.h 93, 217
sys/types.h 93, 121
unistd.h 80, 93, 95, 113, 215
wait.h 118

243
200

/etc/skel 33
213
230
230
213
213
112

alias 33
builtins 31
cat 220
cd 213
chmod 231
chmod +x 23
chown 233
cp 220
fdisk 203
fsck 206
gtk-config 349
insmod 159
ipcs 141
kill 102
killall 104
ldconfig 76
less 220
limit 89
llength 284
ln 222

locate 220
ls 213
mkdir 213
mknod 137, 175
modinfo 169
modprobe 160
mv 220
nice 107
ps 100, 102
pstree 100
renice 107
rm 213, 220
rmdir 213
rmmod 162
setenv 33
strace 404
tac 220
top 105
touch 220
ulimit 89
umount 202
which 220

247
25

111

35
case 28
if 27
188

kernel-source 415
34
HOME 79
LD_LIBRARY_PATH 75
PATH 79
PWD 79
SHELL 79
USER 79

24
24
25
244

413

149
119

chdir() 215
chmod() 232
chown() 233
close() 89, 249
creat() 89, 92
execl() 112, 116
execle() 116
execlp() 116
execve() 114, 115
execvp() 116
fork() 112, 122
getcwd() 229
getgid() 233
getuid() 233
link() 224
lseek() 89, 97
lstat() 217
mkdir() 219
mknod() 137
mount() 210
msgctl() 148
msgget() 143
msgrcv() 147
msgsend() 145
open() 89, 94
opendir() 215
read() 89, 94
readdir() 216
readlink() 224
readv() 89
rename() 223
rewinddir() 217
rmdir() 219
semctl() 152
semget() 150

427

semop() 151
shmat() 155
shmctl() 156
shmdt() 156
shmget() 154
signal() 119
statvfs() 227
symlink() 224
umask() 138, 224
unlink() 223
wait() 117
write() 89, 95
writev() 89
298, 355
249

dirent 216
file_operations 175
ipc_perm 143
mntent 226
msgbuf 141
msqid_ds 142
proc_dir_entry 184
sembuf 151
semid_ds 149
shmid_ds 154
sockadd_in 251
sockadd_in6 251
sockaddr 250
stat 217
statvfs 227
200
15

207

.bash_history 20
/etc/csh.cshrc 32
/etc/csh.login 32
/etc/csh.logout 32
/etc/fstab 205, 206, 226
/etc/ld.so.cache 75
/etc/ld.so.conf 75
/etc/modprobe.conf 160

428

(.)
/etc/modprobe.preload 161
/etc/modules.conf 159
/etc/mtab 226
/etc/profile 20
/etc/protocols 250
/etc/resolv.conf 363
/etc/shells 15
/etc/sysctl.conf 239
/proc/filesystems 234
/proc/kallsyms 172
/proc/mounts 226
~/.bash_logout 20
~/.bash_profile 20
~/.bashrc 20
~/.history 33
Documentation/devices.txt 177
230
202
194, 195, 198
ext2 194
ext3 194
JFS 195
ReiserFS 195
XFS 195
194
326

accept() 253
basename() 229
bind() 249, 250
cleanup_module() 162
clearenv() 82
connect() 249, 252, 253
endmntent() 227
fchdir() 215
fclose() 85
fflush() 87
fgetpos() 87
fgets() 86
fopen() 85, 226
fopendir() 216
fprintf() 86
fputs() 86
freopen() 85
fscanf() 86
fseek() 86
fsetpos() 87
ftell() 87

ftok() 140
g_object_ref() 361
get_user() 183
getenv() 80
gethostbyname() 254
getmntent() 226
getpid() 132
getpwuid() 121
getsockname() 254
getsockopt() 261
gtk_check_button_new() 370
gtk_check_button_new_with_label() 370
gtk_clist_append() 375
gtk_clist_clear() 375
gtk_clist_insert() 375
gtk_clist_new() 375
gtk_clist_new_with_titles() 375
gtk_clist_prepend() 375
gtk_clist_remove() 375
gtk_container_remove() 361
gtk_entry_new() 364
gtk_entry_set_editable() 364
gtk_init() 348
gtk_main() 348
gtk_main_quit() 351
gtk_radio_button_group() 371
gtk_radio_button_new() 370
gtk_radio_button_new_with_label() 370
gtk_signal_connect() 351, 354
gtk_toggle_button_get_active() 371
gtk_toggle_button_set_active() 371
gtk_widget_destroy() 361
gtk_widget_grab_focus() 362
gtk_widget_hide() 362
gtk_widget_show() 362
gtk_window_new() 348
gtk_window_set_default_size() 352
gtk_window_set_title() 348
init_module() 162
ioctl() 183, 264
listen() 253
msg_exists() 148
pclose() 134
popen() 134
printk() 162
pthread() 125
pthread_cancel() 132
pthread_create() 123
pthread_exit() 129

pthread_join() 130
pthread_self() 132
put_user() 180
putenv() 81
recv() 254
recvfrom() 254
register_chrdev() 177
rewind() 87
send() 254
sendto() 254
setenv() 81
setlocale() 360
setmntent() 226
setsockopt() 261
shutdown() 249, 255
socket() 249, 250
system() 107

429

unsetenv() 81
vfscanf() 86
vfsprintf() 86

66
Makefile 66

for 26
while 26

417
419

Вам также может понравиться