1 Лекция № 2 Введение в язык С
2 Для л. р. № 2: • MOVSB|MOVSW|MOVSD • Команды MMX • Pure C NB: 32 -разрядный режим работы. Регистры общего назначения вмещают 4 байта.
3 MOVe String of Bytes 1 байт MOVSB Words 2 байт MOVSW Double Words 4 байт MOVSD
4 MOVSB память=>память • [ESI]=>[EDI] • Direction. Flag = 1? § Нет: § Да: ESI <= ESI+1; EDI <= EDI+1; ESI <= ESI-1; EDI <= EDI-1; Единица обусловлена типом перемещаемых данных. Для MOVSW, например, регистры изменяются на 2.
5 Префикс rep movsb: 1. Выполнить movsb 2. Уменьшить ECX на 1 3. ECX != 0 ? Повторить : следующая команда
6 Пример кода – копия 12 байт cld lea esi, source_string lea edi, dest_string mov ecx, 3 rep movsd После одной итерации movsd: [ESI] Hey, I win!!! [EDI] Hey, f 1=*0&^(#
7 С - план лекции • • • Настройка проекта на компиляцию кода С Конфигурации проекта (Debug, Release) Hello, world и указатели Объявление массивов Extern, объявления функций Не- и стандартные заголовочные файлы. h Препроцессорные директивы (define, ifdef, include) Строки в С, использование printf Различные места в ЛАП, динамическое выделение памяти
8 Настройка проекта • Solution соответствует конечной программе • Project соответствует одному скомпилированному файлу
9
10 Конфигурации проекта Конфигурация включает в себя набор параметров компиляции – настройка должна быть проведена раздельно!
11 Debug и Release • Debug: ▫ ▫ Низкое быстродействие Отсутствие оптимизации Большой размер кода Отладочная информация • Release: ▫ Высокое быстродействие ▫ Компактные исполняемые файлы ▫ Более медленная компиляция
12 Hello, world! #include
13 Указатели Команда: ls –la filename int argc char* ls 00 h char** argv -la 00 h char* filename 00 h Строки нуль-терминированы.
14 Указатели int A = 5; int* p. A = &a; p. A + 1 или p. A++ Адреса различаются на 4!
15 Где-то в памяти: char** argv ls 00 h char* (2) int argc char* (1) -la 00 h char* Filename 00 h (3) Примеры адресной арифметики: *argv == (1) *(argv+1) == (2) **(argv+(argc-1)) == (3)
16 Массивы в С Различие в синтаксисе c: int a[] = {5, 3}; c#: int[] a = {5, 3};
17 Корректное обращение к функции int next(int a) { return a+1; } int main (int argc, char** argv) { return next(-1); }
18 Обьявление функций int next(int); // необходимо объявление int main (int argc, char** argv) { return next(-1); } int next(int a) { return a+1; } Компилятор не знает, каков формат вызова функции next при её фактическом вызове
19 Порядок важен: main. c func. c extern int next(int); int next(int a) { return a+1; } int main (int argc, char** argv) { return next(-1); } extern можно опустить.
20 Заголовочные файлы func. c int next(int a) { return a+1; } int prev(int a) { return a-1; } int same(int a) { return a; } func. h int next(int); int prev(int a); int same(int);
21 Заголовочные файлы main. c #include “func. h” … a = prev(4);
22 Заголовочные файлы Использование стандартных функций: #include
23 Директивы препроцессора #define CONST_VALUE 12 #define FLAG #ifdef FLAG … #endif
24 Директивы препроцессора a. h: main. c int func(int); #include “a. h” #include “b. h” #include “c. h” #include “d. h” int func(int); #include “b. h” #include “c. h” int func(int); d. h: #include “a. h”
25 func. h #ifndef FUNC_H #define FUNC_H int func(int); #endif
26 Модель памяти Код Данные Свободное пространство Стек (растёт вверх) void func(int k) { int a; int b; short q; . . . } q b a адрес возврата k Код Данные Свободное пространство Выделенная память Стек (растёт вверх)
27 Строки в С • Константная неизменяемая строка: ▫ char* string = “string!”; • Строка в стеке: ▫ char string[] = “string!”; • Строка, расположенная в куче
28 Использование printf int i = 5; char* name = “Wutzor”; printf (“%d, tyou win, buddy! %s n”, i, name); %d – спецификатор вывода для integer %s – для строки, принимает указатель (!) Корректность очень важна, контроля типов нет.
29 Динамическое выделение памяти Код Данные Свободное пространство Стек (растёт вверх) • В свободной области находится область динамически выделяемой памяти (куча, heap) • Если она не очищается программистом, память «утекает» (memory leaks) – потребление памяти программой неконтролируемо растёт.
30 malloc #include
31 malloc int i; for (i=0; i<3; ++i) leak(int i); После третьего вызова к 16*3 байтам будет потерян доступ, однако они останутся зарезервированными, и дальнейшие выделения памяти не перекроют их. Код Данные вызов 1 вызов 2 вызов 3 Свободное пространство Стек (растёт вверх)
32 malloc #include
33 Memory leaks • Вся выделенная память должна быть своевременно освобождена. • Как только указатель теряется в силу локальной видимости переменных, память «утекает»