singlepost

Программирование Сокетов, Com, Lpt, USB портов на СИ << На главную или назад  

Суть – две программы – одна передает файл, другая принимает через сокеты,Com, Lpt, USB порты. USB не сделал еще, не могу найти информацию про них.

В чем проблема – при передаче определенных файлов через сокеты, функция fread заканчивает чтение файла не дойдя до конца файла ( на 89 кбайте). Такое случается не на всех файлах, и я не пойму в чем дело.

Вот тут //slil.ru/26523213 проекты Visual Studio 2005. А тут //slil.ru/26523227 только исходники.В папке FileTransfer находятся тестовые файлы для передачи, все файлы кроме test1.txt передаются правильно.

И если кто-то может протестировать на соединении через Com или Lpt, пожалуйста напишите. И если кто-то значет что-то про USB – тоже :-)

Помогите отловить баг, пожалуйста.

17 ответов в теме “Программирование Сокетов, Com, Lpt, USB портов на СИ”

  1. 17
    Илья Антипенко ответил:

    3 – лучше "Переполнение буфера", больше инфы найдешь…

  2. 16
    Cyber Max ответил:

    1- инфы если честно полно… только USB изначально не для этой цели предназначался.. поэтому в и ОС средств таких не закладывали.. не думаю что драйвер чем то поможет.
    3 – ну что тут расказывать.. ты выделил на стеке буфер.. если какая либо операция работы с буфером промажет и вылезет за его граници произойдет перезапись стека.. а занчит данные, а что более печально адресса возврата из подпрограм будут перезаписаны и твой код может скакнуть неизвестно куда.. Второе этим часто пользуются хакеры. Инфы полно.. набери в гугле "Срыв стека" и почитай :)
    4 – многие не многие.. а все обверточные функции в итоге вызовут функции WinApi. Поэтому ты просто потеряешь в производительости. + WinApi намного удобнее в этом плане

  3. 15
    Алексей Руденко ответил:

    1 – поможет в принципе, но не мне
    3 – почитаю
    4 – не думаю, что производительность сильно важна в моей программе

  4. 14
    Cyber Max ответил:

    1- соединить может ты и соединишь.. а вот просто так работать с портом не получиться!
    2- я думаю для того чтобы твою работы оценили по достоинству сделедует задуваться об этом в первую очередь! всего то нужно определить платформо независимые типы и макровы для BE/LE и забыть об этом… осоновной код вообще знать не будет ничего о платформонезависимости!
    3- лучше на стеке ничего такого не хранить! про срыв стека слышал? вот твой код может быть этому подвержен!
    4-лучше отказаться от iostream функций, а сразу использовать WinAPI функции ибо первые есть обвертка над последними!

  5. 13
    Алексей Руденко ответил:

    1 – ага, я знаю, поэтому и нет никакой инфы – единственный выход писать драйвер, но я это не потяну
    3 – не слышал, расскажи или ссылки дай
    4 – почему это лучше? как раз многие говорят, что наоборот лучше.

  6. 12
    Алексей Руденко ответил:

    ну, 1 -через USB можно соединить два компьютера – есть специальные кабели
    2 -платформонезависимый это хорошо, но у меня практическая работа не на это направлена – пусть запускают на Win 32 XP SP2 :-) но я подумаю над этим
    3 – char content[1024], а как еще можно выделить, malloc – это чем-то удобней?
    4 – API функции я заменю на fopen, fwrite and fread. Просто они были первым, что я нашел.

  7. 11
    Cyber Max ответил:

    Инетересно .. а как ты через USB файлы передавать собрался? USB это не NULL-modem! на одной стороне у тебя "хост" на другом "функция" подчинення этому "хосту". Другими словами должно быть устройство. Соединив два компа USB кабелем рескуещь отправить в небыьте свой хост контроллер – это раз.

    Второе при перечади чего либо по сети нужен протокол обмена платформонезависимый. То есть размер переменной отвечающей за передачи размера тела данных должен быть фиксированый на всех платформах (32/64 Bit, BigEndian/Lttle endian) – sizeof(act_size) абсолютно не отвечает этим требованиям!

    Третье – что такое sizeof(content) и чему оно равно? По записи видно что память выделена на стеке.. что не очень правильно!

    Четвертое.. раз ты во WriteFile используешь OVERLAPPED метод.. то где проверка на подтверждение отправки данных в порт?

  8. 10
    Жека Кирпичев ответил:

    Увы, нету.

  9. 9
    Жека Кирпичев ответил:

    А как ты определяешь, что оказываются прочитаны не все байты файла? Самый надежный способ – просуммировать возвращенные fread'ом значения.

  10. 8
    Алексей Руденко ответил:

    всё я нашел его :-) нужно открывать файлы с атрибутом на бинарное чтение ("rb" and "wb"), а то будет на любом нуле прекращаться. Вообще забыл про это. Спасибо, а то еще б долго мучился.

  11. 7
    Алексей Руденко ответил:

    Жека jkff Кирпичев, а у тебя нет случайно COM или LPT кабеля?

  12. 6
    Жека Кирпичев ответил:

    Хм. Хотя нет, вроде не может… Ну, в общем, попробуй все-таки использовать feof/ferror – может, и заработает.

  13. 5
    Алексей Руденко ответил:

    MSDN – fread returns the number of full items actually read, which may be less than count if an error occurs or if the end of the file is encountered before reaching count.
    То есть происходит ошибка или файл закончился, но файл не закончился. Ошибки не должно быть. В других случаях функция не должна возвращать меньше.
    Я попробовал while (!(feof(f) || ferror(f))); – тот же эффект, сейчас попробую на ноль

  14. 4
    Алексей Руденко ответил:

    нет, не работает и при проверке на ноль, чувствую я где-то жестко туплю

  15. 3
    Жека Кирпичев ответил:

    do {
    n_read = fread(&content,sizeof(char), sizeof(content), f);
    act_size = n_read;
    WriteFile(hPort,&act_size,sizeof(act_size),&dw,&ov);
    WriteFile(hPort,content,sizeof(content),&dw,&ov);
    }
    while (n_read == sizeof(content));

    Это неправильно. fread не обязан возвращать столько байтов сколько ты просишь, он в принципе может тебе хоть по одному байту файл отдавать, даже если ты просишь блоками по 64к. Указываемый размер – это твое "пожелание" системе.

    Условие завершения должно быть другое – n_read == 0 или feof(f) || ferror(f).

  16. 2
    Алексей Руденко ответил:

    не, если возвращает меньше, то цикл прекращается. Дело в том, что возвращает меньше, когда еще несколько байт файла осталось – и не во всех файлах

  17. 1
    Жека Кирпичев ответил:

    Вот я и говорю, что оно *может* возвращать меньше, даже когда еще осталось содержимое в файле, *поэтому* проверять конец файла надо не по n_read == sizeof(content), а по n_read == 0.

Клуб программистов работает уже ой-ой-ой сколько, а если поточнее, то с 2007 года.