sscanf с трубами C

У меня проблема с разбором в c с помощью sscanf

Я прочитал текст на консоли с помощью одной функции, называемой read_line()

char cm1[100],cm2[100],cm3[100]
printf("Enter command:");
read_line(var_text);
/*var_text = cat /etc/passwd | cut -f1 d: | sort */
int num = sscanf(var_text,"%s | %s | %s",cm1,cm2,cm3);

Хорошо, если я напишу var_text cat | cut | sort в cm1 return cat, в cm2 вернут cut, а в cm3 вернут sort, но если я напишу cat /etc/passwd | cut -f1 d: | sort , cm1 вернет cat, а cm2 и cm3 нет...

Я сделал оболочку на c, и мне нужны команды и атрибуты

Спасибо за все, и извините за этот плохой английский :)


person Christian    schedule 10.01.2013    source источник


Ответы (1)


Спецификатор формата %s остановит обработку на первом символе пробела. На случай, если:

кот /etc/passwd | вырезать -f1 д: | Сортировать

это будет пробел после cat, на котором заканчивается первый %s. Затем спецификатор формата ожидает |, которого не существует, а cm2 и cm3 не заполнены. Для этого вы можете использовать набор сканирования:

if (3 == sscanf(var_text, "%99[^|]| %99[^|]| %99s", cm1, cm2, cm3))
{
}

Обратите внимание на использование спецификатора ширины для предотвращения переполнения буфера и проверки возвращаемого значения из sscanf(), чтобы убедиться, что все целевые переменные заполнены.

Спецификатор формата %99[^|] указывает, что можно прочитать не более 99 символов (на один меньше, чем размер целевого буфера для размещения нулевого терминатора), пока не встретится символ |.

См. демонстрацию по адресу http://ideone.com/Cz1Qef .

person hmjd    schedule 10.01.2013
comment
вы можете использовать sscanf(var_text, "%m[^|] | %m[^|] | %ms", &cm1, &cm2, &cm3);, чтобы избежать проблемы переполнения буфера. cmx должен быть определен как char * и не забудьте освободить память - person MOHAMED; 10.01.2013
comment
@MohamedKALLEL, я не знаком с %m и не могу найти его в стандарте C99. Это расширение компилятора? - person hmjd; 10.01.2013
comment
это недействительно для всех версий gcc. Подробнее см. следующую ссылку: stackoverflow.com/questions/13863063/ - person MOHAMED; 10.01.2013
comment
при использовании %m чем sscanf будет выделять память - person MOHAMED; 10.01.2013