Акаролибр писал: ↑03.02.2023 14:48
Компилятор ворчит по делу, он корректно обнаружил логическую ошибку в программе.
Если программа работает как надо, то в чём именно ошибка? (За исключением того, что 0 не туда заносится, но это на работу не влияет)
Акаролибр писал: ↑03.02.2023 14:48
Резработчики компилятора молодцы.
С этим я согласен. Учитывая то, что он делает
![:)](./images/smilies/smile.gif)
Правда в нём есть, как я думал, ошибка, но, судя по
man gcc, фича.
Shell
mik13@MiK13:/run/shm$ cat ti.c
#include <stdio.h>
int a[3],i;
int main() {
a[3]=3; a[4]=4; a[5]=5; a[6]=6;
for(i=0;i<7;i++) printf("%d %d\n",i,a[i]);
}
mik13@MiK13:/run/shm$ gcc -o ti ti.c -Wall
mik13@MiK13:/run/shm$
В массиве всего 3 элемента, я записываю числа в 4-й, 5-й, 6-й, 7-й элементы, а компилятор никак на это не реагирует.
Правда, я нашёл, что он начинает реагировать, если включена, как минимум,
-O2.
Довольно странно.
Акаролибр писал: ↑03.02.2023 14:48
Напишем тестовый пример и посмотрим, есть ли ошибки в компиляторе.
...
Проверяем:
Код: Выделить всё
user@localhost:~$ gcc -std=c99 -Wall -O3 -o view_udp view_udp.c
user@localhost:~$ file view_udp
view_udp: ELF 64-bit LSB pie executable, x86-64, version 1 (SYSV), dynamically linked, interpreter /lib64/ld-linux-x86-64.so.2, BuildID[sha1]=81831d375ac4158d2f688fa431b32b8596b82baa, for GNU/Linux 3.2.0, not stripped
user@localhost:~$ du -b view_udp
16664 view_udp
user@localhost:~$
Теперь мы знаем, что в компиляторе ошибки нет. Где же она есть?
Зададим топикстартеру уточняющие вопросы:
1) не перепутан ли порядок передачи аргументов в strncpy ?
2) почему в верхней строке заполняется элемент массива с индексом ii, а в нижней строке ноль добавляется в ДРУГОЙ элемент массива?
3) почему автор постеснялся привести заголок цикла?
4) было ли бы правильно сказать нам версию компилятора, вместо версии Debian, а то вдруг мы на Gentoo?
Я не сомневался, что в компиляторе ошибки нет. По крайней мере в пределах того, что мне приходится делать.
(правда, странно, что для компилятора задание двоичных констант сделали, а формат для него не предусмотрели)
По поводу вопросов.
1) Порядок не перепутан. нужно скопировать строку в текущий элемент из предыдущего
2) Это действительно ошибка. Нужно ноль заносить в элемент с индексом ii. Исправил. Но она на работу не влияет. "Ошибка" (в принципе) есть ниже. Но так как эта программу я написал для себя, не продукт, я дополнительный контроль не вводил (кстати, он вызывает аналогичное предупреждение).
3) Просто меня интересовало что явилось основанием для компилятора для предупреждения.
А текст цикла такой:
Код: Выделить всё
for(i=optind+1;i<argc;i++) { // Для остальных параметров:
ii=i-optind-1;
if(*argv[i]=='.') { // Если параметр "."
ofs[ii]=ofs[ii-1]+step; // Смещение -- на 4 больше предыдущего
strncpy(fmt[ii],fmt[ii-1],15); // Формат -- как у предыдущего
fmt[ii][15]=0;
} else { // Иначе
if(*argv[i]==':') ofs[ii]=ofs[ii-1]+4; // Если в начале параметра ':'
else ofs[ii]=strtol(argv[i],&ac,0);
if(*ac) ac++;
strcpy(fmt[ii],ac); step=4;
if(strstr(ac,"h")) step=2;
if(strstr(ac,"hh")) step=1;
if(strstr(ac,"c")) step=1;
if(strstr(ac,"F")) step=8;
}
}
В этом цикле в элементы fmt[ii] записывается формат, по которому надо будет вывести значение по смещению, записанному в ofs[ii].
Параметры, передаваемые программе, имеют формат <смещение>:<формат>. И если в качестве параметра используется точка, то формат просто копируется из предыдущего. С соответствующей коррекцией смещения.
Акаролибр писал: ↑03.02.2023 14:48
Для справки:
...
У меня всё то же самое