/** * @brief Remove a socket fd from an event context. * * @param event The ssh_event object. * @param fd The fd to remove. * * @returns SSH_OK on success * SSH_ERROR on failure */ int ssh_event_remove_fd(ssh_event event, socket_t fd) { register size_t i, used; int rc = SSH_ERROR; if(event == NULL || event->ctx == NULL) { return SSH_ERROR; } used = event->ctx->polls_used; for (i = 0; i < used; i++) { if(fd == event->ctx->pollfds[i].fd) { ssh_poll_handle p = event->ctx->pollptrs[i]; struct ssh_event_fd_wrapper *pw = p->cb_data; ssh_poll_ctx_remove(event->ctx, p); free(pw); ssh_poll_free(p); rc = SSH_OK; /* restart the loop */ used = event->ctx->polls_used; i = 0; } } return rc; }
/** * @brief remove the poll handle from session and assign them to a event, * when used in blocking mode. * * @param event The ssh_event object * @param session The session to add to the event. * * @returns SSH_OK on success * SSH_ERROR on failure */ int ssh_event_add_session(ssh_event event, ssh_session session) { unsigned int i; ssh_poll_handle p; #ifdef WITH_SERVER struct ssh_iterator *iterator; #endif if(event == NULL || event->ctx == NULL || session == NULL) { return SSH_ERROR; } if(session->default_poll_ctx == NULL) { return SSH_ERROR; } for(i = 0; i < session->default_poll_ctx->polls_used; i++) { p = session->default_poll_ctx->pollptrs[i]; ssh_poll_ctx_remove(session->default_poll_ctx, p); ssh_poll_ctx_add(event->ctx, p); } #ifdef WITH_SERVER iterator = ssh_list_get_iterator(event->sessions); while(iterator != NULL) { if((ssh_session)iterator->data == session) { /* allow only one instance of this session */ return SSH_OK; } iterator = iterator->next; } if(ssh_list_append(event->sessions, session) == SSH_ERROR) { return SSH_ERROR; } #endif return SSH_OK; }
void ssh_poll_free(ssh_poll_handle p) { if(p->ctx != NULL){ ssh_poll_ctx_remove(p->ctx,p); p->ctx=NULL; } SAFE_FREE(p); }
/** * @brief Free a poll context. * * @param ctx Pointer to an already allocated poll context. */ void ssh_poll_ctx_free(ssh_poll_ctx ctx) { if (ctx->polls_allocated > 0) { while (ctx->polls_used > 0){ ssh_poll_handle p = ctx->pollptrs[0]; ssh_poll_ctx_remove(ctx, p); } SAFE_FREE(ctx->pollptrs); SAFE_FREE(ctx->pollfds); } SAFE_FREE(ctx); }
/** * @brief Remove a session object from an event context. * * @param event The ssh_event object. * @param session The session to remove. * * @returns SSH_OK on success * SSH_ERROR on failure */ int ssh_event_remove_session(ssh_event event, ssh_session session) { ssh_poll_handle p; register size_t i, used; int rc = SSH_ERROR; #ifdef WITH_SERVER struct ssh_iterator *iterator; #endif if(event == NULL || event->ctx == NULL || session == NULL) { return SSH_ERROR; } used = event->ctx->polls_used; for(i = 0; i < used; i++) { p = event->ctx->pollptrs[i]; if(p->session == session){ /* * ssh_poll_ctx_remove() decrements * event->ctx->polls_used */ ssh_poll_ctx_remove(event->ctx, p); p->session = NULL; ssh_poll_ctx_add(session->default_poll_ctx, p); rc = SSH_OK; /* * Restart the loop! * A session can initially have two pollhandlers. */ used = event->ctx->polls_used; i = 0; } } #ifdef WITH_SERVER iterator = ssh_list_get_iterator(event->sessions); while(iterator != NULL) { if((ssh_session)iterator->data == session) { ssh_list_remove(event->sessions, iterator); /* there should be only one instance of this session */ break; } iterator = iterator->next; } #endif return rc; }
/** * @brief remove the poll handle from session and assign them to a event, * when used in blocking mode. * * @param event The ssh_event object * @param session The session to add to the event. * * @returns SSH_OK on success * SSH_ERROR on failure */ int ssh_event_add_session(ssh_event event, ssh_session session) { ssh_poll_handle p; #ifdef WITH_SERVER struct ssh_iterator *iterator; #endif if(event == NULL || event->ctx == NULL || session == NULL) { return SSH_ERROR; } if(session->default_poll_ctx == NULL) { return SSH_ERROR; } while (session->default_poll_ctx->polls_used > 0) { p = session->default_poll_ctx->pollptrs[0]; /* * ssh_poll_ctx_remove() decrements * session->default_poll_ctx->polls_used */ ssh_poll_ctx_remove(session->default_poll_ctx, p); ssh_poll_ctx_add(event->ctx, p); /* associate the pollhandler with a session so we can put it back * at ssh_event_free() */ p->session = session; } #ifdef WITH_SERVER iterator = ssh_list_get_iterator(event->sessions); while(iterator != NULL) { if((ssh_session)iterator->data == session) { /* allow only one instance of this session */ return SSH_OK; } iterator = iterator->next; } if(ssh_list_append(event->sessions, session) == SSH_ERROR) { return SSH_ERROR; } #endif return SSH_OK; }
/** * @brief Remove a session object from an event context. * * @param event The ssh_event object. * @param session The session to remove. * * @returns SSH_OK on success * SSH_ERROR on failure */ int ssh_event_remove_session(ssh_event event, ssh_session session) { ssh_poll_handle p; register size_t i, used; int rc = SSH_ERROR; socket_t session_fd; #ifdef WITH_SERVER struct ssh_iterator *iterator; #endif if(event == NULL || event->ctx == NULL || session == NULL) { return SSH_ERROR; } session_fd = ssh_get_fd(session); used = event->ctx->polls_used; for(i = 0; i < used; i++) { if(session_fd == event->ctx->pollfds[i].fd) { p = event->ctx->pollptrs[i]; ssh_poll_ctx_remove(event->ctx, p); ssh_poll_ctx_add(session->default_poll_ctx, p); rc = SSH_OK; } } #ifdef WITH_SERVER iterator = ssh_list_get_iterator(event->sessions); while(iterator != NULL) { if((ssh_session)iterator->data == session) { ssh_list_remove(event->sessions, iterator); /* there should be only one instance of this session */ break; } iterator = iterator->next; } #endif return rc; }
/** * @brief remove a poll handle to the event. * * @param event the ssh_event * * @param p the poll handle */ void ssh_event_remove_poll(ssh_event event, ssh_poll_handle p) { ssh_poll_ctx_remove(event->ctx,p); }