Чтение онлайн

на главную - закладки

Жанры

Linux программирование в примерах
Шрифт:

36

37 printf("BSS Locations:\n");

38 printf("\tAddress of bss_var: %p\n", &bss_var);

39

40 b = sbrk((ptrdiff_t)32); /* увеличить адресное пространство */

41 nb = sbrk((ptrdiff_t)0);

42 printf("Heap Locations:\n");

43 printf("\tInitial end of heap: %p\n", b);

44 printf("\tNew end of heap: %p\n", nb);

45

46 b = sbrk((ptrdiff_t)-16); /*
сократить его */

47 nb = sbrk((ptrdiff_t)0);

48 printf("\tFinal end of heap: %p\n", nb);

49 }

50

51 void

52 afunc(void)

53 {

54 static int level = 0; /* уровень рекурсии */

55 auto int stack_var; /* автоматическая переменная в стеке */

56

57 if (++level == 3) /* избежать бесконечной рекурсии */

58 return;

59

60 printf("\tStack level %d: address of stack_var: %p\n",

61 level, &stack_var);

62 afunc; /* рекурсивный вызов */

63 }

Эта программа распечатывает местонахождение двух функций

main
и
afunc
(строки 22–23). Затем она показывает, как стек растет вниз, позволяя
afunc
(строки 51–63) распечатать адреса последовательных экземпляров ее локальной переменной
stack_var
. (
stack_var
намеренно объявлена как
auto
, чтобы подчеркнуть, что она находится в стеке.) Затем она показывает расположение памяти, выделенной с помощью
alloca
(строки 28–32). В заключение она печатает местоположение переменных данных и BSS (строки 34–38), а затем памяти, выделенной непосредственно через
sbrk
(строки 40–48). Вот результаты запуска программы на системе Intel GNU/Linux:

$ ch03-memaddr

Text Locations:

 Address of main: 0x804838c

 Address of afunc: 0x80484a8

Stack Locations:

 Stack level 1: address of stack_var: 0xbffff864

 Stack level 2: address of stack_var: 0xbffff844

/* Стек растет вниз */

 Start of alloca'ed array: 0xbffff860

 End of alloca'ed array: 0xbffff87f

/* Адреса находятся в стеке */

Data Locations:

 Address of data_var: 0x80496b8

BSS Locations:

 Address of bss_var: 0x80497c4

/* BSS выше инициализированных данных */

Heap Locations:

 Initial end of heap: 0x80497c8

/* Куча непосредственно над BSS */

 New end of heap: 0x80497e8

/* И растет вверх */

 Final end of heap: 0x80497d8

/*
Адресные пространства можно сокращать */

3.3. Резюме

• У каждой программы Linux и (Unix) есть различные области памяти. Они хранятся в разных частях файла исполняемой программы на диске. Некоторые из секций загружаются при запуске программы в одну и ту же область памяти. Все запушенные экземпляры одной и той же программы разделяют исполняемый код (сегмент текста). Программа

size
показывает размеры различных областей переместимых объектных файлов и полностью скомпонованных исполняемых файлов.

• В адресном пространстве запушенной программы могут быть дыры, а размер адресного пространства может изменяться при выделении и освобождении памяти. На современных системах адрес 0 не является частью адресного пространства, поэтому не пытайтесь разыменовывать указатели

NULL
.

• На уровне языка С память выделяется с помощью одной из функций

malloc
,
calloc
или
realloc
. Память освобождается с помощью
free
. (Хотя с помощью
realloc
можно делать все, использование ее таким образом не рекомендуется.) Освобожденная память обычно не удаляется из адресного пространства; вместо этого она используется повторно при последующих выделениях.

• Необходимо предпринять чрезвычайные меры осторожности в следующих случаях

 • освобождать лишь память, выделенную с помощью соответствующих процедур,

 • освобождать память один и только один раз,

 • освобождать неиспользуемую память и

 • не допускать «утечки» динамически выделяемой памяти.

• POSIX предоставляет для удобства функцию

strdup
, a GLIBC предоставляет функции
getline
и
getdelim
для чтения строк произвольной длины. Функции интерфейса низкоуровневых системных вызовов
brk
и
sbrk
предоставляют непосредственный, но примитивный доступ к выделению и освобождению памяти. Если вы не создаете свой собственный распределитель памяти, следует избегать их. Существует функция
alloca
для выделения памяти в стеке, но ее использование не рекомендуется. Подобно умению распознавать ядовитый плющ, про нее нужно знать лишь для того, чтобы избегать ее.

Упражнения

1. Начав со структуры —

struct line {

 size_t buflen;

 char *buf;

 FILE* fp;

};

— напишите свою собственную функцию

readline
, которая будет читать строки любой длины. Не беспокойтесь о строках, продолженных с помощью обратного слеша. Вместо использования
fgetc
для чтения строк используйте
getc
для чтения одного символа за раз.

2. Сохраняет ли ваша функция завершающий символ конца строки? Объясните, почему.

3. Как ваша функция обрабатывает строки, оканчивающиеся CR-LF?

4. Как вы инициализируете структуру? В отдельной процедуре? С помощью документированных условий для определенных значений в структуре?

5. Как вы обозначаете конец файла? Как вы указываете, что возникла ошибка ввода/вывода? Должна ли ваша функция сообщать об ошибках? Объясните, почему.

6. Напишите программу, которая использует вашу функцию для ее тестирования, а также другую программу, создающую входные данные для первой программы. Протестируйте функцию.

Поделиться:
Популярные книги

Кодекс Охотника. Книга XV

Винокуров Юрий
15. Кодекс Охотника
Фантастика:
попаданцы
аниме
5.00
рейтинг книги
Кодекс Охотника. Книга XV

Вечная Война. Книга II

Винокуров Юрий
2. Вечная война.
Фантастика:
юмористическая фантастика
космическая фантастика
8.37
рейтинг книги
Вечная Война. Книга II

Камень. Книга восьмая

Минин Станислав
8. Камень
Фантастика:
фэнтези
боевая фантастика
7.00
рейтинг книги
Камень. Книга восьмая

Огненный князь

Машуков Тимур
1. Багряный восход
Фантастика:
фэнтези
попаданцы
аниме
5.00
рейтинг книги
Огненный князь

Ваше Сиятельство 2

Моури Эрли
2. Ваше Сиятельство
Фантастика:
фэнтези
альтернативная история
аниме
5.00
рейтинг книги
Ваше Сиятельство 2

Сильнейший Столп Империи. Книга 5

Ермоленков Алексей
5. Сильнейший Столп Империи
Фантастика:
аниме
фэнтези
фантастика: прочее
попаданцы
5.00
рейтинг книги
Сильнейший Столп Империи. Книга 5

Виконт. Книга 1. Второе рождение

Юллем Евгений
1. Псевдоним `Испанец`
Фантастика:
фэнтези
боевая фантастика
попаданцы
6.67
рейтинг книги
Виконт. Книга 1. Второе рождение

Я – Легенда 2: геном хищника

Гарцевич Евгений Александрович
2. Я - Легенда!
Фантастика:
боевая фантастика
рпг
фантастика: прочее
попаданцы
5.00
рейтинг книги
Я – Легенда 2: геном хищника

Рыцари порога.Тетралогия

Злотников Роман Валерьевич
Рыцари порога
Фантастика:
боевая фантастика
7.92
рейтинг книги
Рыцари порога.Тетралогия

Князь Андер Арес 2

Грехов Тимофей
2. Андер Арес
Фантастика:
рпг
аниме
фэнтези
фантастика: прочее
5.00
рейтинг книги
Князь Андер Арес 2

Комбинация

Ланцов Михаил Алексеевич
2. Сын Петра
Фантастика:
попаданцы
альтернативная история
5.00
рейтинг книги
Комбинация

Компас желаний

Кас Маркус
8. Артефактор
Фантастика:
городское фэнтези
аниме
фэнтези
5.00
рейтинг книги
Компас желаний

Газлайтер. Том 22

Володин Григорий Григорьевич
22. История Телепата
Фантастика:
боевая фантастика
попаданцы
фэнтези
5.00
рейтинг книги
Газлайтер. Том 22

Чужое наследие

Кораблев Родион
3. Другая сторона
Фантастика:
боевая фантастика
8.47
рейтинг книги
Чужое наследие