В моем клиентском коде я выполняю эти шаги для соединения с сокетом:
Создание сокета
sockDesc = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP)
Соединение его (повторяют в течение 'x' времени в случае отказа),
connect(sockDesc, (sockaddr *) &destAddr, sizeof(destAddr))
(После того, как заполнение destAddr
поля)
Используя сокет для send()
/recv()
операция:
send(sockDesc, buffer, bufferLen, 0)
recv(sockDesc, buffer, bufferLen, 0)
close()
дескриптор сокета и выход
close(sockDesc)
Если во время send()
/recv()
повреждения соединения, я нашел, что мог соединиться путем возврата к шагу 2.
Это решение хорошо? я должен закрыть дескриптор сокета и возвратиться к шагу 1?
Другое интересное наблюдение, что я не могу понять, состоит в том, когда я останавливаю свой сервер эха и запускаю клиент. Я создаю Сокет (шаг 1) и вызов connect()
который перестал работать (как ожидалось), но затем я продолжаю звонить connect()
, позволяет говорят, 10 раз. После 5 повторений я запускаю сервер и connect()
успешно. Но во время send()
звоните это получает SIGPIPE
ошибка. Я хотел бы знать:
1) Сделайте я должен создать новый сокет каждый раз connect()
сбои? Согласно моему пониманию, пока я не выполнил никого send()
/recv()
на сокете это совсем как ново, и я могу снова использовать то же fd
для connect()
звонить.
2) Я не понимаю почему SIGPIPE
получен, когда сервер возрос и connect()
успешно.
Поскольку Холст
не имеет фиксированной ширины и высоты, я бы включил его в Поле просмотра
:
<ItemsControl.ItemsPanel>
<ItemsPanelTemplate>
<Viewbox Stretch="Uniform">
<Canvas x:Name="canvas" Background="DarkSeaGreen">
<Canvas.LayoutTransform>
<ScaleTransform ScaleY="-1" />
</Canvas.LayoutTransform>
</Canvas>
</Viewbox>
</ItemsPanelTemplate>
</ItemsControl.ItemsPanel>
Или поместите весь элемент управления UserControl
в Поле просмотра
.
Если вы хотите поддерживать больше браузеров, чем CSS3, вы можете посмотреть на библиотеку с открытым исходным кодом cufon javascript library
И вот API , если вы хотите сделать больше фанки вещи.
Major Pro: Позволяет делать то, что нужно.
Major Con: Запрещает выбор текста в некоторых браузерах, поэтому использование подходит для текстов заголовков (но вы можете использовать его на всем сайте, если хотите)
-121--998019-Да, необходимо закрыть и вернуться к шагу 1:
close () закрывает дескриптор файла, чтобы оно больше не относилось ни к одному и может использоваться повторно.
Из здесь .
Гнезда, соответствующие нарушенному соединению, находятся в нестабильном состоянии. обычно повторное соединение невозможно, если операционная система не отпустит гнездо.
Я думаю, будет лучше закрыть() и подключиться снова... вам не придется создавать другой сокет.
В любом случае, убедитесь, что вы установили ЛИНГЕР вашего сокета, чтобы гарантировать, что при передаче не будут потеряны данные.
Смотрите http://www.gnu.org/s/libc/manual/html_node/Socket_002dLevel-Options.html#Socket_002dLevel-Options
Используйте сборку OpenJDK, известную для передачи TCK, чтобы минимизировать неожиданности.
-121--1266004-Зумирование от RotateRight ( http://www.rotateright.com ) - это то, что я использовал. Она имеет вид бабочки функций, и вы можете дважды щелкнуть любую функцию, чтобы погрузиться в исходный или asm код. Создайте с помощью отладочной информации (-g), чтобы увидеть источник, но вы все равно должны построить и профилировать оптимизированный код.
-121--855344-Если соединение разорвано и вы пытаетесь записать в дескриптор файла, вы должны получить ошибку/сигнал разрыва канала. Все это говорит о том, что дескриптор файла, который вы пытались записать, больше не имеет никого на другой стороне, чтобы прочитать то, что вы отправляете.
Что вы можете сделать, так это поймать сигнал SIGPIPE, а затем справиться с повторным подключением, закрыв FD и возвращаясь к шагу 1. Теперь у вас будет новый FD, из которого вы можете читать и писать для подключения.
Я думаю, что закрыть сокет - это правильно, несмотря на то, что это может сработать, если вы этого не сделаете.
Сокет, который не удалось подключиться, может быть не в ТОЧНО таком же состоянии, как новый, что может вызвать проблемы позже. Я бы предпочел избежать такой возможности и просто сделаю новую. Это чище.
Сокеты TCP содержат МНОГО состояний, некоторые из которых зависят от реализации и определяются сетью.
Способ состоит в использовании ~/.netrc, как описано на шаге 3 этой документации Git :
Затем добавьте следующее к $ HOME/.netrc (вы можете обойтись без, но будет предложено ввести пароль много раз):
машина < имя _ сервера > вход < имя _ пользователя > пароль < пароль >
... и установить разрешения:
chmod 600 ~/.netrc
Как и в случае git 1,7,9, это, похоже, путь, чтобы пойти будет собственный API поддержки учетных данных. Git поставляется с открытым текстом хранилища учетных данных или менее удобным, но более безопасным временным кэшем учетных данных . Также можно использовать сторонних помощников по работе с учетными данными. На данный момент известно о помощнике для собственного хранилища учетных данных Windows и , который интегрируется с клавиатурой OS X . (Сборка Git, поставляемая Homebrew, имеет двоичный файл, как и другие дистрибутивы OS X Git. Github также предоставляет автономный двоичный .)
Как правило, достаточно настроить помощник учетных данных один раз:
git config --global credential.helper wincred
Или вместо wincred
используйте любой помощник, подходящий для вашей платформы. (Если имя исполняемого файла помощника - git-credential-wincred
, то значение параметра будет равно wincred
и т.д.)
Помощники учетных данных также поддерживают необходимость иметь отдельные наборы учетных данных для различных репозиториев на одном хосте.
-121--961300-Файлы cookie отправляются на сервер по каждому запросу, поэтому, если вы планируете сохранить значительный объем данных, сохраните их в сессии.
В противном случае, если вы храните небольшие объемы данных, файлы cookie будут в порядке.
Любые конфиденциальные данные должны храниться в сеансе, так как файлы cookie не защищены на 100%. Преимуществом файлов cookie является возможность сохранения памяти на сервере, который обычно хранит данные сеанса.
-121--999943-Если в спецификации Single UNIX не говорится, что она ДОЛЖНА работать, чтобы вернуться к шагу # 2, а не к шагу # 1, то тот факт, что это происходит с работой в Linux, является лишь детализацией реализации, и вы были бы намного лучше и более портативны, если бы вы вернулись к шагу # 1. Насколько мне известно, спецификация не гарантирует, что можно вернуться к шагу № 2, и поэтому я бы посоветовал вернуться к шагу № 1.