/* if this urb had a transfer buffer already (old transfer) free it */ if (urb->transfer_buffer != NULL) { kfree(urb->transfer_buffer); urb->transfer_buffer = NULL; } 
/* make sure transfer buffer is freed */ kfree(urb->transfer_buffer); urb->transfer_buffer = NULL; 
static void send_more_port_data(struct edgeport_serial *edge_serial, struct edgeport_port *edge_port){	struct TxFifo	*fifo = &edge_port->txfifo;	struct urb	*urb;	unsigned char	*buffer;	int		status;	int		count;	int		bytesleft;	int		firsthalf;	int		secondhalf;	unsigned long	flags;	dbg("%s(%d)", __FUNCTION__, edge_port->port->number);	spin_lock_irqsave(&edge_port->ep_lock, flags);	if (edge_port->write_in_progress ||	    !edge_port->open             ||	    (fifo->count == 0)) {		dbg("%s(%d) EXIT - fifo %d, PendingWrite = %d", __FUNCTION__, edge_port->port->number, fifo->count, edge_port->write_in_progress);		goto exit_send;	}	// since the amount of data in the fifo will always fit into the	// edgeport buffer we do not need to check the write length	//	Do we have enough credits for this port to make it worthwhile	//	to bother queueing a write. If it's too small, say a few bytes,	//	it's better to wait for more credits so we can do a larger	//	write.	if (edge_port->txCredits < EDGE_FW_GET_TX_CREDITS_SEND_THRESHOLD(edge_port->maxTxCredits,EDGE_FW_BULK_MAX_PACKET_SIZE)) {		dbg("%s(%d) Not enough credit - fifo %d TxCredit %d", __FUNCTION__, edge_port->port->number, fifo->count, edge_port->txCredits );		goto exit_send;	}	// lock this write	edge_port->write_in_progress = TRUE;	// get a pointer to the write_urb	urb = edge_port->write_urb;	/* if this urb had a transfer buffer already (old transfer) free it */	if (urb->transfer_buffer != NULL) {		kfree(urb->transfer_buffer);		urb->transfer_buffer = NULL;	}	/* build the data header for the buffer and port that we are about to send out */	count = fifo->count;	buffer = kmalloc (count+2, GFP_ATOMIC);	if (buffer == NULL) {		dev_err(&edge_port->port->dev, "%s - no more kernel memory...\n", __FUNCTION__);		edge_port->write_in_progress = FALSE;		goto exit_send;	}	buffer[0] = IOSP_BUILD_DATA_HDR1 (edge_port->port->number - edge_port->port->serial->minor, count);	buffer[1] = IOSP_BUILD_DATA_HDR2 (edge_port->port->number - edge_port->port->serial->minor, count);	/* now copy our data */	bytesleft =  fifo->size - fifo->tail;	firsthalf = min (bytesleft, count);	memcpy(&buffer[2], &fifo->fifo[fifo->tail], firsthalf);	fifo->tail  += firsthalf;	fifo->count -= firsthalf;	if (fifo->tail == fifo->size) {		fifo->tail = 0;	}	secondhalf = count-firsthalf;	if (secondhalf) {		memcpy(&buffer[2+firsthalf], &fifo->fifo[fifo->tail], secondhalf);		fifo->tail  += secondhalf;		fifo->count -= secondhalf;	}	if (count)		usb_serial_debug_data(debug, &edge_port->port->dev, __FUNCTION__, count, &buffer[2]);	/* fill up the urb with all of our data and submit it */	usb_fill_bulk_urb (urb, edge_serial->serial->dev, 		       usb_sndbulkpipe(edge_serial->serial->dev, edge_serial->bulk_out_endpoint),		       buffer, count+2, edge_bulk_out_data_callback, edge_port);	/* decrement the number of credits we have by the number we just sent */	edge_port->txCredits -= count;	edge_port->icount.tx += count;	urb->dev = edge_serial->serial->dev;	status = usb_submit_urb(urb, GFP_ATOMIC);	if (status) {		/* something went wrong */		dev_err(&edge_port->port->dev, "%s - usb_submit_urb(write bulk) failed, status = %d, data lost\n", __FUNCTION__, status);		edge_port->write_in_progress = FALSE;		/* revert the credits as something bad happened. */		edge_port->txCredits += count;		edge_port->icount.tx -= count;	}	dbg("%s wrote %d byte(s) TxCredit %d, Fifo %d", __FUNCTION__, count, edge_port->txCredits, fifo->count);exit_send:	spin_unlock_irqrestore(&edge_port->ep_lock, flags);}
4520	/local/tlutelli/issta_data/temp/c/2005_temp/2005/4520/1bc3c9e1e44c2059fe2ffa6ff70ad0a925d7b05f/io_edgeport.c/clean/drivers/usb/serial/io_edgeport.c