/* event_send_start -- prepare to send a event message to subscriber * * This gets complicated because: * -- The message is sent via TCP and we have to keep the stream open * for 30 seconds to get a response... then close it. * -- But we might have other event happen in the meantime... * we have to queue them, if we lose them then the subscriber will * be forced to unsubscribe and subscribe again. * -- If multiple URLs are provided then we are supposed to try successive * ones after 30 second timeout. * -- The URLs might use domain names instead of dotted decimal addresses, * and resolution of those may cause unwanted sleeping. * -- Doing the initial TCP connect can take a while, so we have to come * back after connection and then send the data. * * Returns nonzero on error; * * Prerequisite: No current event send (s->current_event == NULL) * and non-empty queue. */ static int event_send_start(struct subscription *s) { struct wps_event_ *e; int itry; /* * Assume we are called ONLY with no current event and ONLY with * nonempty event queue and ONLY with at least one address to send to. */ assert(s->addr_list != NULL); assert(s->current_event == NULL); assert(s->event_queue != NULL); s->current_event = e = event_dequeue(s); /* Use address acc. to no. of retries */ e->addr = s->addr_list; for (itry = 0; itry < e->retry; itry++) e->addr = e->addr->next; e->sd = socket(AF_INET, SOCK_STREAM, 0); if (e->sd < 0) { event_retry(e, 0); return -1; } /* set non-blocking so we don't sleep waiting for connection */ if (fcntl(e->sd, F_SETFL, O_NONBLOCK) != 0) { event_retry(e, 0); return -1; } /* * Start the connect. It might succeed immediately but more likely will * return errno EINPROGRESS. */ if (connect(e->sd, (struct sockaddr *) &e->addr->saddr, sizeof(e->addr->saddr))) { if (errno != EINPROGRESS) { event_retry(e, 1); return -1; } } /* Call back when ready for writing (or on failure...). */ if (eloop_register_sock(e->sd, EVENT_TYPE_WRITE, event_send_tx_ready, NULL, e)) { event_retry(e, 0); return -1; } e->sd_registered = 1; /* Don't wait forever! */ if (eloop_register_timeout(EVENT_TIMEOUT_SEC, 0, event_timeout_handler, NULL, e)) { event_retry(e, 0); return -1; } return 0; }
/* event_delete_all -- delete entire event queue and current event */ void event_delete_all(struct subscription *s) { struct wps_event_ *e; while ((e = event_dequeue(s)) != NULL) event_delete(e); if (s->current_event) { event_delete(s->current_event); /* will set: s->current_event = NULL; */ } }
void act_mevt_a(int8 id) { int8 event; if(event_dequeue(&id, &event) != RET_OK) { CMD_RESP_RET(RET_NO_DATA, VAL_NONE); } if(id <= ATC_SOCK_NUM_END && event == SOCKEVENT_RECV) EVENT_RESP_SIZE(id, event, GetSocketRxRecvBufferSize(id)); else EVENT_RESP(id, event); }
/** * event_add - Add a new event to a queue * @s: Subscription * @data: Event data (is copied; caller retains ownership) * @probereq: Whether this is a Probe Request event * Returns: 0 on success, -1 on error, 1 on max event queue limit reached */ int event_add(struct subscription *s, const struct wpabuf *data, int probereq) { struct wps_event_ *e; unsigned int len; len = dl_list_len(&s->event_queue); if (len >= MAX_EVENTS_QUEUED) { wpa_printf(MSG_DEBUG, "WPS UPnP: Too many events queued for " "subscriber %p", s); if (probereq) return 1; /* Drop oldest entry to allow EAP event to be stored. */ e = event_dequeue(s); if (!e) return 1; event_delete(e); } if (s->last_event_failed && probereq && len > 0) { /* * Avoid queuing frames for subscribers that may have left * without unsubscribing. */ wpa_printf(MSG_DEBUG, "WPS UPnP: Do not queue more Probe " "Request frames for subscription %p since last " "delivery failed", s); return -1; } e = os_zalloc(sizeof(*e)); if (e == NULL) return -1; dl_list_init(&e->list); e->s = s; e->data = wpabuf_dup(data); if (e->data == NULL) { os_free(e); return -1; } e->subscriber_sequence = s->next_subscriber_sequence++; if (s->next_subscriber_sequence == 0) s->next_subscriber_sequence++; wpa_printf(MSG_DEBUG, "WPS UPnP: Queue event %p for subscriber %p " "(queue len %u)", e, s, len + 1); dl_list_add_tail(&s->event_queue, &e->list); event_send_all_later(s->sm); return 0; }
/* event_send_start -- prepare to send a event message to subscriber * * This gets complicated because: * -- The message is sent via TCP and we have to keep the stream open * for 30 seconds to get a response... then close it. * -- But we might have other event happen in the meantime... * we have to queue them, if we lose them then the subscriber will * be forced to unsubscribe and subscribe again. * -- If multiple URLs are provided then we are supposed to try successive * ones after 30 second timeout. * -- The URLs might use domain names instead of dotted decimal addresses, * and resolution of those may cause unwanted sleeping. * -- Doing the initial TCP connect can take a while, so we have to come * back after connection and then send the data. * * Returns nonzero on error; * * Prerequisite: No current event send (s->current_event == NULL) * and non-empty queue. */ static int event_send_start(struct subscription *s) { struct wps_event_ *e; unsigned int itry; struct wpabuf *buf; /* * Assume we are called ONLY with no current event and ONLY with * nonempty event queue and ONLY with at least one address to send to. */ if (dl_list_empty(&s->addr_list) || s->current_event || dl_list_empty(&s->event_queue)) return -1; s->current_event = e = event_dequeue(s); /* Use address according to number of retries */ itry = 0; dl_list_for_each(e->addr, &s->addr_list, struct subscr_addr, list) if (itry++ == e->retry) break; if (itry < e->retry) return -1; buf = event_build_message(e); if (buf == NULL) { event_retry(e, 0); return -1; } e->http_event = http_client_addr(&e->addr->saddr, buf, 0, event_http_cb, e); if (e->http_event == NULL) { wpabuf_free(buf); event_retry(e, 0); return -1; } return 0; }
void dequeue_loop(void) { Event_t e = event_dequeue(); if (e != EVENT_NULL) { // analyse des évènements #if KBS_ANALYSER unsigned long last_process_time = micros(); #endif execute_callback(e); // analyse des évènements #if KBS_ANALYSER busy_time += micros() - last_process_time; #endif } }
static void detach(void) { event_dequeue(&nmi_event); }