Beispiel #1
0
void *aggregate_thread(void *queue_ptr) {
	struct pa_entry *pae = NULL;
	struct da_entry *dae = NULL;
	struct ga_entry *gae = NULL;
	struct s_aggregate *aggregates = NULL;
	// char buf[255];

	log_debug("starting aggregate thread");
	while (1) {
		pthread_mutex_lock(&pa_mutex);
		pthread_cond_wait(&pa_cond, &pa_mutex);

		pae = SIMPLEQ_FIRST(&pa_head);
		SIMPLEQ_REMOVE_HEAD(&pa_head, pa_entries);
		pthread_mutex_unlock(&pa_mutex);

		update_aggregates(pae->packet);
		free(pae);

		if (has_aggregates()) {
			aggregates = get_aggregates();

			if (!(dae = (struct da_entry *)malloc(sizeof(struct da_entry)))) {
				log_error("aggregate_thread: dae: malloc failed");
			}

			dae->values = aggregates;
			dae->timestamp = time(NULL);

			pthread_mutex_lock(&da_mutex);
			SIMPLEQ_INSERT_TAIL(&da_head, dae, da_entries);
			pthread_cond_signal(&da_cond);
			pthread_mutex_unlock(&da_mutex);

			if (!(gae = (struct ga_entry *)malloc(sizeof(struct ga_entry)))) {
				log_error("aggregate_thread: gae: malloc failed");
			}

			gae->values = aggregates;
			gae->timestamp = dae->timestamp;

			pthread_mutex_lock(&ga_mutex);
			SIMPLEQ_INSERT_TAIL(&ga_head, gae, ga_entries);
			pthread_cond_signal(&ga_cond);
			pthread_mutex_unlock(&ga_mutex);
		}

	}
	return 0;
}
Beispiel #2
0
//Calls down on the semaphore whose purpose is to take a lock
void down( semaphore_t* sem ){
  struct entry *np;
  //mutual exclusion lock
  pthread_mutex_lock(&sem->mutex);
  //check if there are no more "locks" available
  if(sem->count<=0){
    ++sem->wakeupCount;


    //This is where I want to insert the conditional to the queue

    //create the new conditional object using the struct entry
    np = (struct entry *) malloc( sizeof( struct entry ) );
    SIMPLEQ_INSERT_TAIL( &sem->conditionalQueue, np, next );

    pthread_cleanup_push(cleanup_handler,sem);
    pthread_cond_wait(&np->condition,&sem->mutex);
    pthread_cleanup_pop(0);
  }

  --sem->count;

  //mutual exclusion unlock
  pthread_mutex_unlock(&sem->mutex);
}
Beispiel #3
0
void *serial_thread(void *queue_ptr) {
	char raw_packet[254] = "\0";
	struct rp_entry *rpe = NULL;
	// char buf[255];

	log_debug("starting serial thread");
	while (1) {

		if (serial_readln(raw_packet) == 0) {
			if (!(rpe = (struct rp_entry *)malloc(sizeof(struct rp_entry)))) {
				log_debug("serial_thread: malloc failed");
				return NULL;
			}

			// (void)snprintf(buf, sizeof(buf), "received: %s", raw_packet);
			// log_debug(buf);

			rpe->payload = raw_packet;
			pthread_mutex_lock(&rp_mutex);
			SIMPLEQ_INSERT_TAIL(&rp_head, rpe, rp_entries);
			pthread_cond_signal(&rp_cond);
			pthread_mutex_unlock(&rp_mutex);
		}

	}

	return 0;
}
Beispiel #4
0
/*
 * void cardslot_event_throw(struct cardslot_softc *sc, int ev)
 *
 *   This function throws an event to the event handler.  If the state
 *   of a slot is changed, it should be noticed using this function.
 */
void
cardslot_event_throw(struct cardslot_softc *sc, int ev)
{
	struct cardslot_event *ce;

	DPRINTF(("cardslot_event_throw: an event %s comes\n",
	    ev == CARDSLOT_EVENT_INSERTION_CB ? "CardBus Card inserted" :
	    ev == CARDSLOT_EVENT_INSERTION_16 ? "16-bit Card inserted" :
	    ev == CARDSLOT_EVENT_REMOVAL_CB ? "CardBus Card removed" :
	    ev == CARDSLOT_EVENT_REMOVAL_16 ? "16-bit Card removed" : "???"));

	if ((ce = (struct cardslot_event *)malloc(sizeof(struct cardslot_event),
	    M_TEMP, M_NOWAIT)) == NULL) {
		panic("cardslot_event");
	}

	ce->ce_type = ev;

	{
		int s = spltty();
		SIMPLEQ_INSERT_TAIL(&sc->sc_events, ce, ce_q);
		splx(s);
	}

	wakeup(&sc->sc_events);
}
Beispiel #5
0
int
set_vn(struct fuse *f, struct fuse_vnode *v)
{
    struct fuse_vn_head *vn_head;
    struct fuse_vnode *vn;

    DPRINTF("%s: create or update vnode %llu@%llu = %s\n", __func__,
            (unsigned long long)v->ino, (unsigned long long)v->parent,
            v->path);

    if (tree_set(&f->vnode_tree, v->ino, v) == NULL)
        return (0);

    if (!dict_check(&f->name_tree, v->path)) {
        vn_head = malloc(sizeof(*vn_head));
        if (vn_head == NULL)
            return (0);
        SIMPLEQ_INIT(vn_head);
    } else {
        vn_head = dict_get(&f->name_tree, v->path);
        if (vn_head == NULL)
            return (0);
    }

    SIMPLEQ_FOREACH(vn, vn_head, node) {
        if (v->parent == vn->parent && v->ino == vn->ino)
            return (1);
    }

    SIMPLEQ_INSERT_TAIL(vn_head, v, node);
    dict_set(&f->name_tree, v->path, vn_head);

    return (1);
}
Beispiel #6
0
static void network_notifier(RECOVERY_STATUS status, int error, const char *msg)
{
    int len = msg ? strlen(msg) : 0;
    struct msg_elem *newmsg = (struct msg_elem *)calloc(1, sizeof(*newmsg) + len + 1);
    struct msg_elem *oldmsg;

    if (!newmsg)
        return;

    pthread_mutex_lock(&msglock);
    nrmsgs++;
    if (nrmsgs > NUM_CACHED_MESSAGES) {
        oldmsg = SIMPLEQ_FIRST(&notifymsgs);
        SIMPLEQ_REMOVE_HEAD(&notifymsgs, next);
        free(oldmsg);
        nrmsgs--;
    }
    newmsg->msg = (char *)newmsg + sizeof(struct msg_elem);

    newmsg->status = status;
    newmsg->error = error;

    if (msg) {
        strncpy(newmsg->msg, msg, len);
        clean_msg(newmsg->msg, '\t');
        clean_msg(newmsg->msg, '\n');
        clean_msg(newmsg->msg, '\r');
    }


    SIMPLEQ_INSERT_TAIL(&notifymsgs, newmsg, next);
    pthread_mutex_unlock(&msglock);
}
Beispiel #7
0
/*
 * Create the necessary pcmcia function structures to alleviate the lack
 * of any CIS information on this device.
 * Actually, we hijack the fake function created by the pcmcia framework.
 */
int
cfxga_install_function(struct pcmcia_function *pf)
{
	struct pcmcia_config_entry *cfe;

	/* Get real. */
	pf->pf_flags &= ~PFF_FAKE;

	/* Tell the pcmcia framework where the CCR is. */
	pf->ccr_base = 0x800;
	pf->ccr_mask = 0x67;

	/* Create a simple cfe. */
	cfe = (struct pcmcia_config_entry *)malloc(sizeof *cfe,
	    M_DEVBUF, M_NOWAIT);
	if (cfe == NULL) {
		DPRINTF(("%s: cfe allocation failed\n", __func__));
		return (ENOMEM);
	}

	bzero(cfe, sizeof *cfe);
	cfe->number = 42;	/* have to put some value... */
	cfe->flags = PCMCIA_CFE_IO16;
	cfe->iftype = PCMCIA_IFTYPE_MEMORY;

	SIMPLEQ_INSERT_TAIL(&pf->cfe_head, cfe, cfe_list);

	pcmcia_function_init(pf, cfe);
	return (0);
}
Beispiel #8
0
static void
add_bindmount(char *bm)
{
	struct bindmnt *bmnt;
	char *b, *src, *dest;
	size_t len;

	src = strdup(bm);
	assert(src);
	dest = strchr(bm, ':');
	if (dest == NULL || *dest == '\0') {
		errno = EINVAL;
		die("invalid argument for bindmount: %s", bm);
	}
	dest++;
	b = strchr(bm, ':');
	len = strlen(bm) - strlen(b);
	src[len] = '\0';

	bmnt = malloc(sizeof(struct bindmnt));
	assert(bmnt);

	bmnt->src = src;
	bmnt->dest = dest;
	SIMPLEQ_INSERT_TAIL(&bindmnt_queue, bmnt, entries);
}
Beispiel #9
0
Datei: umidi.c Projekt: bluhm/sys
static int
out_jack_output(struct umidi_jack *j, int d)
{
	struct umidi_endpoint *ep = j->endpoint;
	struct umidi_softc *sc = ep->sc;
	int s;

	if (usbd_is_dying(sc->sc_udev))
		return 1;
	if (!j->opened)
		return 1;
	s = splusb();
	if (ep->busy) {
		if (!j->intr) {
			SIMPLEQ_INSERT_TAIL(&ep->intrq, j, intrq_entry);
			ep->pending++;
			j->intr = 1;
		}		
		splx(s);
		return 0;
	}
	if (!out_build_packet(j->cable_number, &j->packet, d,
		ep->buffer + ep->used)) {
		splx(s);
		return 1;
	}
	ep->used += UMIDI_PACKET_SIZE;
	if (ep->used == ep->packetsize) {
		ep->busy = 1;
		start_output_transfer(ep);
	}
	splx(s);
	return 1;
}
Beispiel #10
0
static void
ucomstart(struct tty *tp)
{
	struct ucom_softc *sc = device_lookup_private(&ucom_cd,
	    UCOMUNIT(tp->t_dev));
	struct ucom_buffer *ub;
	int s;
	u_char *data;
	int cnt;

	if (sc->sc_dying)
		return;

	s = spltty();
	if (ISSET(tp->t_state, TS_BUSY | TS_TIMEOUT | TS_TTSTOP)) {
		DPRINTFN(4,("ucomstart: no go, state=0x%x\n", tp->t_state));
		goto out;
	}
	if (sc->sc_tx_stopped)
		goto out;

	if (!ttypull(tp))
		goto out;

	/* Grab the first contiguous region of buffer space. */
	data = tp->t_outq.c_cf;
	cnt = ndqb(&tp->t_outq, 0);

	if (cnt == 0) {
		DPRINTF(("ucomstart: cnt==0\n"));
		goto out;
	}

	ub = SIMPLEQ_FIRST(&sc->sc_obuff_free);
	KASSERT(ub != NULL);
	SIMPLEQ_REMOVE_HEAD(&sc->sc_obuff_free, ub_link);

	if (SIMPLEQ_FIRST(&sc->sc_obuff_free) == NULL)
		SET(tp->t_state, TS_BUSY);

	if (cnt > sc->sc_obufsize)
		cnt = sc->sc_obufsize;

	if (sc->sc_methods->ucom_write != NULL)
		sc->sc_methods->ucom_write(sc->sc_parent, sc->sc_portno,
					   ub->ub_data, data, &cnt);
	else
		memcpy(ub->ub_data, data, cnt);

	ub->ub_len = cnt;
	ub->ub_index = 0;

	SIMPLEQ_INSERT_TAIL(&sc->sc_obuff_full, ub, ub_link);

	softint_schedule(sc->sc_si);

 out:
	splx(s);
}
Beispiel #11
0
void
_rtld_objlist_push_tail(Objlist *list, Obj_Entry *obj)
{
	Objlist_Entry *elm;

	elm = NEW(Objlist_Entry);
	elm->obj = obj;
	SIMPLEQ_INSERT_TAIL(list, elm, link);
}
static int
ld_ataraid_start_span(struct ld_softc *ld, struct buf *bp)
{
	struct ld_ataraid_softc *sc = (void *) ld;
	struct ataraid_array_info *aai = sc->sc_aai;
	struct ataraid_disk_info *adi;
	struct cbuf *cbp;
	char *addr;
	daddr_t bn;
	long bcount, rcount;
	u_int comp;

	/* Allocate component buffers. */
	addr = bp->b_data;

	/* Find the first component. */
	comp = 0;
	adi = &aai->aai_disks[comp];
	bn = bp->b_rawblkno;
	while (bn >= adi->adi_compsize) {
		bn -= adi->adi_compsize;
		adi = &aai->aai_disks[++comp];
	}

	bp->b_resid = bp->b_bcount;

	for (bcount = bp->b_bcount; bcount > 0; bcount -= rcount) {
		rcount = bp->b_bcount;
		if ((adi->adi_compsize - bn) < btodb(rcount))
			rcount = dbtob(adi->adi_compsize - bn);

		cbp = ld_ataraid_make_cbuf(sc, bp, comp, bn, addr, rcount);
		if (cbp == NULL) {
			/* Free the already allocated component buffers. */
                       while ((cbp = SIMPLEQ_FIRST(&sc->sc_cbufq)) != NULL) {
                               SIMPLEQ_REMOVE_HEAD(&sc->sc_cbufq, cb_q);
				CBUF_PUT(cbp);
			}
                       return EAGAIN;
		}

		/*
		 * For a span, we always know we advance to the next disk,
		 * and always start at offset 0 on that disk.
		 */
		adi = &aai->aai_disks[++comp];
		bn = 0;

               SIMPLEQ_INSERT_TAIL(&sc->sc_cbufq, cbp, cb_q);
		addr += rcount;
	}

	/* Now fire off the requests. */
       softint_schedule(sc->sc_sih_cookie);

       return 0;
}
Beispiel #13
0
/*
 *  Scan through a PCI expansion ROM, and create subregions for each
 *  ROM image. This function assumes that the ROM is mapped at
 *  (tag,handle), and that the expansion ROM address decoder is
 *  enabled. The PCI specification requires that no other BAR should
 *  be accessed while the ROM is enabled, so interrupts should be
 *  disabled.
 *
 * XXX This routine is way too pessimistic and returns as soon as it encounters
 * a problem, although not being able to malloc or read a particular image
 * may not prevent further images from being read successfully.
 */
int
cardbus_read_exrom(bus_space_tag_t romt, bus_space_handle_t romh,
    struct cardbus_rom_image_head *head)
{
	size_t addr = 0; /* offset of current rom image */
	size_t dataptr;
	unsigned int rom_image = 0;
	size_t image_size;
	struct cardbus_rom_image *image;
	u_int16_t val;

	SIMPLEQ_INIT(head);
	do {
		val = READ_INT16(romt, romh, addr + CARDBUS_EXROM_SIGNATURE);
		if (val != 0xaa55) {
			DPRINTF(("%s: bad header signature in ROM image "
			    "%u: 0x%04x\n", __func__, rom_image, val));
			return (1);
		}
		dataptr = addr + READ_INT16(romt, romh,
		    addr + CARDBUS_EXROM_DATA_PTR);

		/* get the ROM image size, in blocks */
		image_size = READ_INT16(romt, romh,
		    dataptr + CARDBUS_EXROM_DATA_IMAGE_LENGTH);
		/* XXX
		 * Some ROMs seem to have this as zero, can we assume
		 * this means 1 block?
		 */
		if (image_size == 0)
			image_size = 1;
		image_size <<= 9;

		image = malloc(sizeof(*image), M_DEVBUF, M_NOWAIT);
		if (image == NULL) {
			DPRINTF(("%s: out of memory\n", __func__));
			return (1);
		}
		image->rom_image = rom_image;
		image->image_size = image_size;
		image->romt = romt;
		if (bus_space_subregion(romt, romh, addr,
		    image_size, &image->romh)) {
			DPRINTF(("%s: bus_space_subregion failed", __func__));
			free(image, M_DEVBUF, sizeof(*image));
			return (1);
		}
		SIMPLEQ_INSERT_TAIL(head, image, next);
		addr += image_size;
		rom_image++;
	} while ((bus_space_read_1(romt, romh,
	    dataptr + CARDBUS_EXROM_DATA_INDICATOR) & 0x80) == 0);

	return (0);
}
/*
 * Initialize the link sockets module.
 */
void
lnksock_init(void)
{
	unsigned int slot;

	/* Initialize the list of free link sockets. */
	SIMPLEQ_INIT(&lnk_freelist);

	for (slot = 0; slot < __arraycount(lnk_array); slot++)
		SIMPLEQ_INSERT_TAIL(&lnk_freelist, &lnk_array[slot], lnk_next);
}
Beispiel #15
0
/*
 * If we failed to allocate uba resources, put us on a queue to wait
 * until there is available resources. Resources to compete about
 * are map registers and BDPs. This is normally only a problem on
 * Unibus systems, Qbus systems have more map registers than usable.
 */
void
uba_enqueue(struct uba_unit *uu)
{
	struct uba_softc *uh;
	int s;

	uh = device_private(device_parent(uu->uu_dev));

	s = spluba();
	SIMPLEQ_INSERT_TAIL(&uh->uh_resq, uu, uu_resq);
	splx(s);
}
Beispiel #16
0
/*
 * If we failed to allocate uba resources, put us on a queue to wait
 * until there is available resources. Resources to compete about
 * are map registers and BDPs. This is normally only a problem on
 * Unibus systems, Qbus systems have more map registers than usable.
 */
void
uba_enqueue(struct uba_unit *uu)
{
	struct uba_softc *uh;
	int s;

	uh = (void *)((struct device *)(uu->uu_softc))->dv_parent;

	s = splvm();
	SIMPLEQ_INSERT_TAIL(&uh->uh_resq, uu, uu_resq);
	splx(s);
}
Beispiel #17
0
int
fsd_equeue_insert(fsd_evt_t *evt)
{
	struct fsd_equeue_entry *entry;
	
	if ((entry = (struct fsd_equeue_entry*)malloc(sizeof(struct fsd_equeue_entry))) == NULL)
		return (ERR_MEMORY);
	
	entry->evt = evt;
	SIMPLEQ_INSERT_TAIL(&fsd_equeue_head, entry, entries);
	
	return (ERR_OK);
}
Beispiel #18
0
/*
 * Each device that needs some handling if an ubareset occurs must
 * register for reset first through this routine.
 */
void
uba_reset_establish(void (*reset)(device_t), device_t dev)
{
	struct uba_softc *uh = device_private(device_parent(dev));
	struct uba_reset *ur;

	ur = malloc(sizeof(struct uba_reset), M_DEVBUF, M_NOWAIT|M_ZERO);
	if (ur == NULL)
		panic("uba_reset_establish");
	ur->ur_dev = dev;
	ur->ur_reset = reset;

	SIMPLEQ_INSERT_TAIL(&uh->uh_resetq, ur, ur_resetq);
}
Beispiel #19
0
/*
 * Each device that needs some handling if an ubareset occurs must
 * register for reset first through this routine.
 */
void
uba_reset_establish(void (*reset)(struct device *), struct device *dev)
{
	struct uba_softc *uh = (void *)dev->dv_parent;
	struct uba_reset *ur;

	ur = malloc(sizeof(struct uba_reset), M_DEVBUF, M_NOWAIT);
	if (ur == NULL)
		panic("uba_reset_establish");
	ur->ur_dev = dev;
	ur->ur_reset = reset;

	SIMPLEQ_INSERT_TAIL(&uh->uh_resetq, ur, ur_resetq);
}
Beispiel #20
0
/*
 * Defer the creation of a kernel thread.  Once the standard kernel threads
 * and processes have been created, this queue will be run to callback to
 * the caller to create threads for e.g. file systems and device drivers.
 */
void
kthread_create_deferred(void (*func)(void *), void *arg)
{
	struct kthread_q *kq;

	kq = malloc(sizeof *kq, M_TEMP, M_NOWAIT);
	if (kq == NULL)
		panic("unable to allocate kthread_q");
	bzero(kq, sizeof *kq);

	kq->kq_func = func;
	kq->kq_arg = arg;

	SIMPLEQ_INSERT_TAIL(&kthread_q, kq, kq_q);
}
Beispiel #21
0
int rudp_send(Rudp *rudp, uint8_t *buf, uint32_t len)
{
    if (rudp==NULL || (len>0 && buf==NULL)) {
        return -1;
    }
    Segment *seg = segment_new(sizeof(*seg) + len);
    if (seg==NULL) {
        return -2;
    }
    if (len>0) {
        memcpy(seg->data, buf, len);
    }
    SIMPLEQ_INSERT_TAIL(&rudp->snd_buf, seg);
    return 0;
}
Beispiel #22
0
void
pcic_queue_event(struct pcic_handle *h, int event)
{
	struct pcic_event *pe;
	int s;

	pe = malloc(sizeof(*pe), M_TEMP, M_NOWAIT);
	if (pe == NULL)
		panic("pcic_queue_event: can't allocate event");

	pe->pe_type = event;
	s = splhigh();
	SIMPLEQ_INSERT_TAIL(&h->events, pe, pe_q);
	splx(s);
	wakeup(&h->events);
}
Beispiel #23
0
Datei: dt.c Projekt: MarginC/kame
int
dt_intr(void *cookie)
{
	struct dt_softc *sc;
	struct dt_msg *msg, *pend;

	sc = cookie;

	switch (dt_msg_get(&sc->sc_msg, 1)) {
	case DT_GET_ERROR:
		/*
		 * Ugh! The most common occurrence of a data overrun is upon
		 * a key press and the result is a software generated "stuck
		 * key".  All I can think to do is fake an "all keys up"
		 * whenever a data overrun occurs.
		 */
		sc->sc_msg.src = dt_kbd_addr;
		sc->sc_msg.ctl = DT_CTL(1, 0, 0);
		sc->sc_msg.body[0] = DT_KBD_EMPTY;
#ifdef DIAGNOSTIC
		printf("%s: data overrun or stray interrupt\n",
		    sc->sc_dv.dv_xname);
#endif
		break;

	case DT_GET_DONE:
		break;

	case DT_GET_NOTYET:
		return (1);
	}

	if ((msg = SLIST_FIRST(&sc->sc_free)) == NULL) {
		printf("%s: input overflow\n", sc->sc_dv.dv_xname);
		return (1);
	}
	SLIST_REMOVE_HEAD(&sc->sc_free, chain.slist);
	memcpy(msg, &sc->sc_msg, sizeof(*msg));

	pend = SIMPLEQ_FIRST(&sc->sc_queue);
	SIMPLEQ_INSERT_TAIL(&sc->sc_queue, msg, chain.simpleq);
	if (pend == NULL)
		softintr_schedule(sc->sc_sih);

	return (1);
}
Beispiel #24
0
/*
 * Initialize the transmit descriptors.
 */
static void
rtk_list_tx_init(struct rtk_softc *sc)
{
	struct rtk_tx_desc *txd;
	int i;

	while ((txd = SIMPLEQ_FIRST(&sc->rtk_tx_dirty)) != NULL)
		SIMPLEQ_REMOVE_HEAD(&sc->rtk_tx_dirty, txd_q);
	while ((txd = SIMPLEQ_FIRST(&sc->rtk_tx_free)) != NULL)
		SIMPLEQ_REMOVE_HEAD(&sc->rtk_tx_free, txd_q);

	for (i = 0; i < RTK_TX_LIST_CNT; i++) {
		txd = &sc->rtk_tx_descs[i];
		CSR_WRITE_4(sc, txd->txd_txaddr, 0);
		SIMPLEQ_INSERT_TAIL(&sc->rtk_tx_free, txd, txd_q);
	}
}
/*
 * If a CCB is specified, enqueue it.  Pull CCBs off the software queue in
 * the order that they were enqueued and try to submit their command blocks
 * to the controller for execution.
 */
void
twe_ccb_enqueue(struct twe_softc *sc, struct twe_ccb *ccb)
{
	int s;

	s = splbio();

	if (ccb != NULL)
		SIMPLEQ_INSERT_TAIL(&sc->sc_ccb_queue, ccb, ccb_chain.simpleq);

	while ((ccb = SIMPLEQ_FIRST(&sc->sc_ccb_queue)) != NULL) {
		if (twe_ccb_submit(sc, ccb))
			break;
		SIMPLEQ_REMOVE_HEAD(&sc->sc_ccb_queue, ccb_chain.simpleq);
	}

	splx(s);
}
Beispiel #26
0
static usbd_status
ucomsubmitread(struct ucom_softc *sc, struct ucom_buffer *ub)
{
	usbd_status err;

	usbd_setup_xfer(ub->ub_xfer, sc->sc_bulkin_pipe,
	    (usbd_private_handle)sc, ub->ub_data, sc->sc_ibufsize,
	    USBD_SHORT_XFER_OK | USBD_NO_COPY, USBD_NO_TIMEOUT, ucomreadcb);

	if ((err = usbd_transfer(ub->ub_xfer)) != USBD_IN_PROGRESS) {
		/* XXX: Recover from this, please! */
		printf("ucomsubmitread: err=%s\n", usbd_errstr(err));
		return (err);
	}

	SIMPLEQ_INSERT_TAIL(&sc->sc_ibuff_empty, ub, ub_link);

	return (USBD_NORMAL_COMPLETION);
}
Beispiel #27
0
static void
ucom_write_status(struct ucom_softc *sc, struct ucom_buffer *ub,
    usbd_status err)
{
	struct tty *tp = sc->sc_tty;
	uint32_t cc = ub->ub_len;

	switch (err) {
	case USBD_IN_PROGRESS:
		ub->ub_index = ub->ub_len;
		break;
	case USBD_STALLED:
		ub->ub_index = 0;
		softint_schedule(sc->sc_si);
		break;
	case USBD_NORMAL_COMPLETION:
		usbd_get_xfer_status(ub->ub_xfer, NULL, NULL, &cc, NULL);
#if defined(__NetBSD__) && NRND > 0
		rnd_add_uint32(&sc->sc_rndsource, cc);
#endif
		/*FALLTHROUGH*/
	default:
		SIMPLEQ_REMOVE_HEAD(&sc->sc_obuff_full, ub_link);
		SIMPLEQ_INSERT_TAIL(&sc->sc_obuff_free, ub, ub_link);
		cc -= sc->sc_opkthdrlen;

		CLR(tp->t_state, TS_BUSY);
		if (ISSET(tp->t_state, TS_FLUSH))
			CLR(tp->t_state, TS_FLUSH);
		else
			ndflush(&tp->t_outq, cc);

		if (err != USBD_CANCELLED && err != USBD_IOERROR &&
		    !sc->sc_dying) {
			if ((ub = SIMPLEQ_FIRST(&sc->sc_obuff_full)) != NULL)
				ucom_submit_write(sc, ub);

			(*tp->t_linesw->l_start)(tp);
		}
		break;
	}
}
Beispiel #28
0
static void
workqueue_finiqueue(struct workqueue *wq, struct workqueue_queue *q)
{
	struct workqueue_exitargs wqe;

	KASSERT(wq->wq_func == workqueue_exit);

	wqe.wqe_q = q;
	KASSERT(SIMPLEQ_EMPTY(&q->q_queue));
	KASSERT(q->q_worker != NULL);
	mutex_enter(&q->q_mutex);
	SIMPLEQ_INSERT_TAIL(&q->q_queue, &wqe.wqe_wk, wk_entry);
	cv_signal(&q->q_cv);
	while (q->q_worker != NULL) {
		cv_wait(&q->q_cv, &q->q_mutex);
	}
	mutex_exit(&q->q_mutex);
	mutex_destroy(&q->q_mutex);
	cv_destroy(&q->q_cv);
}
Beispiel #29
0
/*
 * Enqueue the specified command (if any) and attempt to start all enqueued
 * commands.
 */
static int
cac_ccb_start(struct cac_softc *sc, struct cac_ccb *ccb)
{

	KASSERT(mutex_owned(&sc->sc_mutex));

	if (ccb != NULL)
		SIMPLEQ_INSERT_TAIL(&sc->sc_ccb_queue, ccb, ccb_chain);

	while ((ccb = SIMPLEQ_FIRST(&sc->sc_ccb_queue)) != NULL) {
		if ((*sc->sc_cl.cl_fifo_full)(sc))
			return (EAGAIN);
		SIMPLEQ_REMOVE_HEAD(&sc->sc_ccb_queue, ccb_chain);
#ifdef DIAGNOSTIC
		ccb->ccb_flags |= CAC_CCB_ACTIVE;
#endif
		(*sc->sc_cl.cl_submit)(sc, ccb);
	}

	return (0);
}
void
cpc_mainbus_attach(device_t parent, device_t self, void *aux)
{
	struct genppc_pci_chipset_businfo *pbi;

	genppc_pct = malloc(sizeof(struct genppc_pci_chipset), M_DEVBUF,
	    M_NOWAIT);
	pmppc_pci_get_chipset_tag(genppc_pct);
	pbi = malloc(sizeof(struct genppc_pci_chipset_businfo),
	    M_DEVBUF, M_NOWAIT);
	KASSERT(pbi != NULL);
	pbi->pbi_properties = prop_dictionary_create();
	KASSERT(pbi->pbi_properties != NULL);
	SIMPLEQ_INIT(&genppc_pct->pc_pbi);
	SIMPLEQ_INSERT_TAIL(&genppc_pct->pc_pbi, pbi, next);

	cpc_attach(self, genppc_pct, &pmppc_mem_tag, &pmppc_pci_io_tag,
		   &pci_bus_dma_tag, a_config.a_is_monarch,
		   a_config.a_bus_freq);

	if (!a_config.a_is_monarch)
		aprint_error_dev(self, "not Monarch, pci not attached\n");
}