Как установить время ожидания в Connect / Send?(as400 iseries v5r4, rpg) - PullRequest
0 голосов
/ 19 августа 2010

Из этого учебника сокетов rpg мы создали клиент сокетов в rpg, который вызывает сокет java-сервера

Проблема в том, что блоки операций connect () / send () блокируются, и у нас есть требование, что если соединение / send не может быть выполнено за считанные секунды, мы должны просто зарегистрировать его и завершить.

Если я установлю сокет в неблокирующий режим (я думаю, с помощью fnctl), мы не до конца понимаем, как поступить, и не можем найти никакой полезной документации с примерами для этого.

Я думаю, что если я подключаюсь к неблокирующему сокету, мне нужно выбрать select (..., timeout), который сообщает нам, если подключение выполнено успешно и / мы можем отправить (в байтах). Но если мы отправим (в байтах) впоследствии, так как теперь это неблокирующий сокет (который будет возвращаться сразу после вызова), как я узнаю, что send () осуществил фактическую отправку байтов на сервер перед закрытием сокет?

Я могу использовать клиентский сокет в AS400 как процедуру Java или C, но я действительно хочу оставить его в простой программе RPG.

Кто-нибудь поможет мне понять, как это сделать, пожалуйста? Спасибо!

1 Ответ

2 голосов
/ 29 августа 2010

На мой взгляд, у того учебника RPG, о котором вы упоминаете, есть небольшой недостаток. Я полагаю, что ваше замешательство вызывает следующий код раздела :

...
Следовательно, мы обычно называем API send () вот так:

D miscdata        S             25A
D rc              S             10I 0

C                   eval      miscdata = 'The data to send goes here'
C                   eval      rc = send(s: %addr(miscdata): 25: 0)
c                   if        rc < 25
C*  for some reason we weren't able to send all 25 bytes!
C                   endif

...

Если вы прочитаете документацию send(), вы увидите, что возвращаемое значение не указывает на ошибку, если оно больше -1, но в приведенном выше коде кажется, что ошибка произошла. Фактически, сумма возвращаемых значений должна равняться размеру буфера, предполагая, что вы продолжаете перемещать указатель в буфер, чтобы отразить то, что было отправлено. Посмотрите здесь в Руководство Биджа по сетевому программированию . Возможно, вы также захотите взглянуть на книгу Ричарда Стивенса Сетевое программирование в UNIX, том 1 , чтобы получить действительно подробные объяснения.

Что касается проблемы определения, была ли последняя отправка перед close() действительной отправкой ... хорошо, параграф выше объясняет, как определить, какая часть данных была отправлена. Однако, вызов close() попытается отправить все неотправленные данные, если не установлено SO_LINGER.

fnctl() используется для управления блокировкой, а setsockopt() используется для установки SO_LINGER.

Абстракция используемых сетевых коммуникаций - это BSD-сокеты. Существуют небольшие различия в реализациях в разных ОС, но, как правило, они довольно однородны. Это означает, что обычно можно использовать документацию, написанную для других ОС, для широкого обзора. Большую часть времени .

...