Пример #1
0
static int VmbusOnISR(struct hv_driver *drv)
{
	int ret = 0;
	int cpu = smp_processor_id();
	void *page_addr;
	struct hv_message *msg;
	union hv_synic_event_flags *event;

	page_addr = gHvContext.synICMessagePage[cpu];
	msg = (struct hv_message *)page_addr + VMBUS_MESSAGE_SINT;

	DPRINT_ENTER(VMBUS);

	/* Check if there are actual msgs to be process */
	if (msg->Header.MessageType != HvMessageTypeNone) {
		DPRINT_DBG(VMBUS, "received msg type %d size %d",
				msg->Header.MessageType,
				msg->Header.PayloadSize);
		ret |= 0x1;
	}

	/* TODO: Check if there are events to be process */
	page_addr = gHvContext.synICEventPage[cpu];
	event = (union hv_synic_event_flags *)page_addr + VMBUS_MESSAGE_SINT;

	/* Since we are a child, we only need to check bit 0 */
	if (test_and_clear_bit(0, (unsigned long *) &event->Flags32[0])) {
		DPRINT_DBG(VMBUS, "received event %d", event->Flags32[0]);
		ret |= 0x2;
	}

	DPRINT_EXIT(VMBUS);
	return ret;
}
Пример #2
0
/*
 * read out all the action frame which are queued in the driver even
 * before issuing any wl cmd. This is essential because due to late arrival of frame it can
 * get queued after the read expires.
 */
void
rwl_wifi_purge_actionframes(void *wl)
{
	dot11_action_wifi_vendor_specific_t *rec_frame;
	void *ptr = NULL;

	if ((rec_frame = (dot11_action_wifi_vendor_specific_t *)
	malloc(RWL_WIFI_ACTION_FRAME_SIZE)) == NULL) {
		DPRINT_DBG(OUTPUT, "Purge Error in reading the frame \n");
		return;
	}

	for (;;) {
		if (rwl_var_getbuf(wl, RWL_WIFI_GET_ACTION_CMD, rec_frame,
		RWL_WIFI_ACTION_FRAME_SIZE, &ptr) < 0) {
			DPRINT_DBG(OUTPUT, "rwl_wifi_purge_actionframes:"
			"Purge Error in reading the frame \n");
			break;
		}
		memcpy((char*)rec_frame, ptr, RWL_WIFI_ACTION_FRAME_SIZE);

		if ((rec_frame->category != RWL_ACTION_WIFI_CATEGORY))
			break;
	}

	free(rec_frame);

	return;
}
Пример #3
0
static void DumpMonitorPage(struct hv_monitor_page *MonitorPage)
{
	int i = 0;
	int j = 0;

	DPRINT_DBG(VMBUS, "monitorPage - %p, trigger state - %d",
		   MonitorPage, MonitorPage->TriggerState);

	for (i = 0; i < 4; i++)
		DPRINT_DBG(VMBUS, "trigger group (%d) - %llx", i,
			   MonitorPage->TriggerGroup[i].AsUINT64);

	for (i = 0; i < 4; i++) {
		for (j = 0; j < 32; j++) {
			DPRINT_DBG(VMBUS, "latency (%d)(%d) - %llx", i, j,
				   MonitorPage->Latency[i][j]);
		}
	}
	for (i = 0; i < 4; i++) {
		for (j = 0; j < 32; j++) {
			DPRINT_DBG(VMBUS, "param-conn id (%d)(%d) - %d", i, j,
			       MonitorPage->Parameter[i][j].ConnectionId.Asu32);
			DPRINT_DBG(VMBUS, "param-flag (%d)(%d) - %d", i, j,
				MonitorPage->Parameter[i][j].FlagNumber);
		}
	}
}
Пример #4
0
int RingBufferWrite(RING_BUFFER_INFO *OutRingInfo,
		    struct scatterlist *sglist, u32 sgcount)
{
	int i = 0;
	u32 byteAvailToWrite;
	u32 byteAvailToRead;
	u32 totalBytesToWrite = 0;

	struct scatterlist *sg;
	volatile u32 nextWriteLocation;
	u64 prevIndices = 0;
	unsigned long flags;

	DPRINT_ENTER(VMBUS);

	for_each_sg(sglist, sg, sgcount, i)
	{
		totalBytesToWrite += sg->length;
	}

	totalBytesToWrite += sizeof(u64);

	spin_lock_irqsave(&OutRingInfo->ring_lock, flags);

	GetRingBufferAvailBytes(OutRingInfo,
				&byteAvailToRead,
				&byteAvailToWrite);

	DPRINT_DBG(VMBUS, "Writing %u bytes...", totalBytesToWrite);

	/* DumpRingInfo(OutRingInfo, "BEFORE "); */

	/* If there is only room for the packet, assume it is full. */
	/* Otherwise, the next time around, we think the ring buffer */
	/* is empty since the read index == write index */
	if (byteAvailToWrite <= totalBytesToWrite) {
		DPRINT_DBG(VMBUS,
			"No more space left on outbound ring buffer "
			"(needed %u, avail %u)",
			totalBytesToWrite,
			byteAvailToWrite);

		spin_unlock_irqrestore(&OutRingInfo->ring_lock, flags);

		DPRINT_EXIT(VMBUS);

		return -1;
	}

	/* Write to the ring buffer */
	nextWriteLocation = GetNextWriteLocation(OutRingInfo);

	for_each_sg(sglist, sg, sgcount, i)
	{
		nextWriteLocation = CopyToRingBuffer(OutRingInfo,
						     nextWriteLocation,
						     sg_virt(sg),
						     sg->length);
	}
/*++

Name: 
	RingBufferRead()

Description:
	Read and advance the read index

--*/
int
RingBufferRead(
	RING_BUFFER_INFO*	InRingInfo,
	PVOID				Buffer,
	UINT32				BufferLen,
	UINT32				Offset
	)
{
	UINT32 bytesAvailToWrite;
	UINT32 bytesAvailToRead;
	UINT32 nextReadLocation=0;
	UINT64 prevIndices=0;

	ASSERT(BufferLen > 0);
	
	SpinlockAcquire(InRingInfo->RingLock);

	GetRingBufferAvailBytes(InRingInfo, &bytesAvailToRead, &bytesAvailToWrite);

	DPRINT_DBG(VMBUS, "Reading %u bytes...", BufferLen);

	//DumpRingInfo(InRingInfo, "BEFORE ");

	// Make sure there is something to read
	if (bytesAvailToRead < BufferLen )
	{
		DPRINT_DBG(VMBUS, "got callback but not enough to read <avail to read %d read size %d>!!", bytesAvailToRead, BufferLen);

		SpinlockRelease(InRingInfo->RingLock);

		return -1;
	}

	nextReadLocation = GetNextReadLocationWithOffset(InRingInfo, Offset);

	nextReadLocation = CopyFromRingBuffer(InRingInfo,
											Buffer,
											BufferLen,
											nextReadLocation);

	nextReadLocation = CopyFromRingBuffer(InRingInfo,
											&prevIndices,
											sizeof(UINT64),
											nextReadLocation);

	// Make sure all reads are done before we update the read index since 
	// the writer may start writing to the read area once the read index is updated
	MemoryFence();

	// Update the read index
	SetNextReadLocation(InRingInfo, nextReadLocation);
	
	//DumpRingInfo(InRingInfo, "AFTER ");

	SpinlockRelease(InRingInfo->RingLock);

	return 0;
}
Пример #6
0
int RingBufferWrite(RING_BUFFER_INFO *OutRingInfo,
		    struct scatterlist *sglist, u32 sgcount)
{
	int i=0;
	u32 byteAvailToWrite;
	u32 byteAvailToRead;
	u32 totalBytesToWrite=0;

	struct scatterlist *sg;
	volatile u32 nextWriteLocation;
	u64 prevIndices=0;
	unsigned long flags;

	DPRINT_ENTER(VMBUS);

	for_each_sg(sglist, sg, sgcount, i)
	{
		totalBytesToWrite += sg->length;
	}

	totalBytesToWrite += sizeof(u64);

	spin_lock_irqsave(&OutRingInfo->ring_lock, flags);

	GetRingBufferAvailBytes(OutRingInfo, &byteAvailToRead, &byteAvailToWrite);

	DPRINT_DBG(VMBUS, "Writing %u bytes...", totalBytesToWrite);

	

	
	
	if (byteAvailToWrite <= totalBytesToWrite)
	{
		DPRINT_DBG(VMBUS, "No more space left on outbound ring buffer (needed %u, avail %u)", totalBytesToWrite, byteAvailToWrite);

		spin_unlock_irqrestore(&OutRingInfo->ring_lock, flags);

		DPRINT_EXIT(VMBUS);

		return -1;
	}

	
	nextWriteLocation = GetNextWriteLocation(OutRingInfo);

	for_each_sg(sglist, sg, sgcount, i)
	{
		nextWriteLocation = CopyToRingBuffer(OutRingInfo,
						     nextWriteLocation,
						     sg_virt(sg),
						     sg->length);
	}
Пример #7
0
/*
 * Heartbeat functionality.
 * Every two seconds, Hyper-V send us a heartbeat request message.
 * we respond to this message, and Hyper-V knows we are alive.
 */
static void heartbeat_onchannelcallback(void *context)
{
	struct vmbus_channel *channel = context;
	u8 *buf;
	u32 buflen, recvlen;
	u64 requestid;
	struct icmsg_hdr *icmsghdrp;
	struct heartbeat_msg_data *heartbeat_msg;

	DPRINT_ENTER(VMBUS);

	buflen = PAGE_SIZE;
	buf = kmalloc(buflen, GFP_ATOMIC);

	VmbusChannelRecvPacket(channel, buf, buflen, &recvlen, &requestid);

	if (recvlen > 0) {
		DPRINT_DBG(VMBUS, "heartbeat packet: len=%d, requestid=%lld",
			   recvlen, requestid);

		icmsghdrp = (struct icmsg_hdr *)&buf[
			sizeof(struct vmbuspipe_hdr)];

		icmsghdrp = (struct icmsg_hdr *)&buf[
				sizeof(struct vmbuspipe_hdr)];

		if (icmsghdrp->icmsgtype == ICMSGTYPE_NEGOTIATE) {
			prep_negotiate_resp(icmsghdrp, NULL, buf);
		} else {
			heartbeat_msg = (struct heartbeat_msg_data *)&buf[
				sizeof(struct vmbuspipe_hdr) +
				sizeof(struct icmsg_hdr)];

			DPRINT_DBG(VMBUS, "heartbeat seq = %lld",
				   heartbeat_msg->seq_num);

			heartbeat_msg->seq_num += 1;
		}

		icmsghdrp->icflags = ICMSGHDRFLAG_TRANSACTION
			| ICMSGHDRFLAG_RESPONSE;

		VmbusChannelSendPacket(channel, buf,
				       recvlen, requestid,
				       VmbusPacketTypeDataInBand, 0);
	}

	kfree(buf);

	DPRINT_EXIT(VMBUS);
}
/*++

Name: 
	CopyFromRingBuffer()

Description:
	Helper routine to copy to source from ring buffer.
	Assume there is enough room. Handles wrap-around in src case only!!

--*/
UINT32
CopyFromRingBuffer(
	RING_BUFFER_INFO	*RingInfo,	
	PVOID				Dest, 
	UINT32				DestLen, 
	UINT32				StartReadOffset)
{
	/* Fixme:  This should not be a void pointer! */
	PVOID ringBuffer=GetRingBuffer(RingInfo);
	UINT32 ringBufferSize=GetRingBufferSize(RingInfo);

	UINT32 fragLen;

	if (DestLen > ringBufferSize - StartReadOffset) // wrap-around detected at the src
	{
		DPRINT_DBG(VMBUS, "src wrap-around detected!");

		fragLen = ringBufferSize - StartReadOffset;

		/* Fixme:  Cast needed due to void pointer */
		memcpy(Dest, (UCHAR *)ringBuffer + StartReadOffset, fragLen);
		/* Fixme:  Cast needed due to void pointer */
		memcpy((UCHAR *)Dest + fragLen, ringBuffer, DestLen - fragLen);
	}
	else
	{
		/* Fixme:  Cast needed due to void pointer */
		memcpy(Dest, (UCHAR *)ringBuffer + StartReadOffset, DestLen);
	}

	StartReadOffset += DestLen;
	StartReadOffset %= ringBufferSize;

	return StartReadOffset;
}
Пример #9
0
static void shutdown_onchannelcallback(void *context)
{
	struct vmbus_channel *channel = context;
	u32 recvlen;
	u64 requestid;
	u8  execute_shutdown = false;

	struct shutdown_msg_data *shutdown_msg;

	struct icmsg_hdr *icmsghdrp;
	struct icmsg_negotiate *negop = NULL;

	vmbus_recvpacket(channel, shut_txf_buf,
			 PAGE_SIZE, &recvlen, &requestid);

	if (recvlen > 0) {
		DPRINT_DBG(VMBUS, "shutdown packet: len=%d, requestid=%lld",
			   recvlen, requestid);

		icmsghdrp = (struct icmsg_hdr *)&shut_txf_buf[
			sizeof(struct vmbuspipe_hdr)];

		if (icmsghdrp->icmsgtype == ICMSGTYPE_NEGOTIATE) {
			prep_negotiate_resp(icmsghdrp, negop, shut_txf_buf);
		} else {
			shutdown_msg =
				(struct shutdown_msg_data *)&shut_txf_buf[
					sizeof(struct vmbuspipe_hdr) +
					sizeof(struct icmsg_hdr)];

			switch (shutdown_msg->flags) {
			case 0:
			case 1:
				icmsghdrp->status = HV_S_OK;
				execute_shutdown = true;

				DPRINT_INFO(VMBUS, "Shutdown request received -"
					    " gracefull shutdown initiated");
				break;
			default:
				icmsghdrp->status = HV_E_FAIL;
				execute_shutdown = false;

				DPRINT_INFO(VMBUS, "Shutdown request received -"
					    " Invalid request");
				break;
			};
		}

		icmsghdrp->icflags = ICMSGHDRFLAG_TRANSACTION
			| ICMSGHDRFLAG_RESPONSE;

		vmbus_sendpacket(channel, shut_txf_buf,
				       recvlen, requestid,
				       VM_PKT_DATA_INBAND, 0);
	}

	if (execute_shutdown == true)
		orderly_poweroff(false);
}
Пример #10
0
/*
 * Send the response to the remote if the channel of the server matches with the
 * server channel.
 */
void remote_wifi_response(void* wl)
{
#ifdef RWL_WIFI
	dot11_action_wifi_vendor_specific_t *list;

	if ((list = rwl_wifi_allocate_actionframe()) == NULL) {
		DPRINT_DBG(OUTPUT, "remote_wifi_response: Failed to allocate frame \n");
		return;
	}

	/* it's sync frame and received from client */
	memcpy((char*)&list->data[RWL_WIFI_CDC_HEADER_OFFSET],
	&g_rem_pkt_ptr[RWL_WIFI_CDC_HEADER_OFFSET], REMOTE_SIZE);
	memcpy((char*)&list->data[REMOTE_SIZE], g_rem_pkt_ptr->message,
	RWL_WIFI_FRAG_DATA_SIZE);
	list->type = RWL_WIFI_FIND_MY_PEER;
	/* Store the client mac addr */
	memcpy((void*)&rwlea, (void*)&list->data[RWL_DUT_MAC_ADDRESS_OFFSET], ETHER_ADDR_LEN);
	/* send the response to client if server is on the same channel */
	rwl_wifi_find_server_response(wl, list);

	free(list);
#else
	UNUSED_PARAMETER(wl);
#endif /* RWL_WIFI */
	return;
}
/* Function to get the shell response from the file */
int
remote_shell_async_get_resp(char* shell_fname, char* buf_ptr, int msg_len)
{
	int sts = 0;
	FILE *shell_fpt;

	shell_fpt = fopen(shell_fname, "rb");

	if (shell_fpt == NULL) {
		DPRINT_ERR(ERR, "\nShell Cmd:File open error\n");
		return sts;
	}

	/* If there is any response from the shell, Read the file and 
	 * update the buffer for the shell response
	 * else Just send the return value of the command executed
	 */
	if (g_shellsync_pid != SHELL_ASYNCCMD_ID) {
		if (msg_len)
			sts  = fread(buf_ptr, sizeof(char), msg_len, shell_fpt);
		fscanf(shell_fpt, "%2x", &sts);
	}
	else
		sts  = fread(buf_ptr, sizeof(char), MAX_SHELL_CMD_LENTH, shell_fpt);

	fclose(shell_fpt);

	remove(shell_fname);

	DPRINT_DBG(OUTPUT, "\n Resp buff from shell cmdis %s\n", buf_ptr);

	return sts;
}
Пример #12
0
/*
 * NetVscInitialize - Main entry point
 */
int NetVscInitialize(struct hv_driver *drv)
{
	struct netvsc_driver *driver = (struct netvsc_driver *)drv;

	DPRINT_DBG(NETVSC, "sizeof(struct hv_netvsc_packet)=%zd, "
		   "sizeof(struct nvsp_message)=%zd, "
		   "sizeof(struct vmtransfer_page_packet_header)=%zd",
		   sizeof(struct hv_netvsc_packet),
		   sizeof(struct nvsp_message),
		   sizeof(struct vmtransfer_page_packet_header));

	/* Make sure we are at least 2 pages since 1 page is used for control */
	/* ASSERT(driver->RingBufferSize >= (PAGE_SIZE << 1)); */

	drv->name = gDriverName;
	memcpy(&drv->deviceType, &gNetVscDeviceType, sizeof(struct hv_guid));

	/* Make sure it is set by the caller */
	/* FIXME: These probably should still be tested in some way */
	/* ASSERT(driver->OnReceiveCallback); */
	/* ASSERT(driver->OnLinkStatusChanged); */

	/* Setup the dispatch table */
	driver->Base.OnDeviceAdd	= NetVscOnDeviceAdd;
	driver->Base.OnDeviceRemove	= NetVscOnDeviceRemove;
	driver->Base.OnCleanup		= NetVscOnCleanup;

	driver->OnSend			= NetVscOnSend;

	RndisFilterInit(driver);
	return 0;
}
int
rwl_read_serial_port(void* hndle, char* read_buf, uint data_size, uint *numread)
{
	int ret;
	uint total_numread = 0;
	while (total_numread < data_size) {
		ret = read(*(int *)hndle, read_buf, data_size - total_numread);
		*numread = ret;
		if (ret == -1) {

			perror("ReadFromPort Failed");
			DPRINT_ERR(ERR, "Errno:%d\n", errno);
			return FAIL;
		}
		if (*numread != data_size - total_numread) {
			DPRINT_DBG(OUTPUT, "asked for %d bytes got %d bytes\n",
			data_size - total_numread, *numread);
		}
		if (*numread == 0)
			break;

		total_numread += *numread;
		read_buf += *numread;
	}
	return SUCCESS;
}
/* Transmit the response in the opened TCP stream socket */
int
rwl_send_to_streamsocket(int SocketDes, const char* SendBuff, int data_size, int Flag)
{
	int total_numwritten = 0,  numwritten = 0;
	while (total_numwritten < data_size) {
		if ((numwritten = send(SocketDes, SendBuff,
			data_size - total_numwritten, Flag)) == -1) {
			perror("Failed to send()");
			DPRINT_ERR(ERR, "\n errno:%d\n", errno);
			return (FAIL);
		}

		/* Sent successfully at first attempt no more retries */
		if (numwritten == data_size) {
			total_numwritten = numwritten;
			break;
		}

		/* If socket is busy we may hit this condition */
		if (numwritten != data_size - total_numwritten) {
			DPRINT_DBG(OUTPUT, "wanted to send %d bytes sent only %d bytes\n",
				data_size - total_numwritten, numwritten);
		}

		/* Now send the remaining buffer */
		total_numwritten += numwritten;
		SendBuff += numwritten;
	}

	return total_numwritten;
}
/* Receive the response from the opened TCP stream socket */
int
rwl_receive_from_streamsocket(int SocketDes, char* RecvBuff, int data_size, int Flag)
{
	int numread;
	int total_numread = 0;

	while (total_numread < data_size) {
		if ((numread = recv(SocketDes, RecvBuff, data_size - total_numread, Flag)) == -1) {
			perror("Failed to Receive()");
			DPRINT_ERR(ERR, "\n errno:%d\n", errno);
			return FAIL;
		}

		if (numread != data_size - total_numread) {
			DPRINT_DBG(OUTPUT, "asked %d bytes got %d bytes\n",
				data_size - total_numread, numread);
		}

		if (numread == 0)
			break;

		total_numread += numread;
		RecvBuff += numread;
	}

	return numread;
}
Пример #16
0
int
rwl_read_serial_port(void* hndle, char* read_buf, uint data_size, uint *numread)
{
	uint total_numread = 0;
	int c = 0;

	while (total_numread < data_size) {
		if (ReadFile(hndle, read_buf, data_size - total_numread, numread, NULL) == 0) {
			DPRINT_ERR(ERR, "rwl_read_serial_port failed with:%d", WSAGetLastError());
			return FAIL;
		}
		if (*numread != data_size - total_numread) {
			c++;
			DPRINT_DBG(OUTPUT, "asked %d bytes got %d bytes\n",
				data_size - total_numread, *numread);
			if (c > MAX_SERIAL_READ_RETRY) {
			        DPRINT_ERR(ERR, "rwl_read_serial_port failed: "
				           "reached max retry limit.\n");
				return FAIL;
			}
			Sleep(10);
		}

		total_numread += *numread;
		read_buf += *numread;
	}
	return SUCCESS;
}
Пример #17
0
static int
rwl_wifi_shellresp(void *wl, rem_ioctl_t *rem_ptr, uchar *input_buf)
{
	int pid, msg_len, error;
	g_sig_ctrlc = 1;
	g_child_pid = pid = rwl_shell_createproc(wl);
	if (pid == 0)
	{
		while (g_sig_ctrlc);
		remote_CDC_tx(wl, 0, input_buf, 0, 0, CTRLC_FLAG, 0);
		exit(0);
	}

	do {
		if ((error = remote_CDC_DATA_wifi_rx_frag(wl, rem_ptr, 0,
		NULL, RWL_WIFI_SHELL_CMD)) < 0) {
			DPRINT_DBG(OUTPUT, "rwl_shell_information_fe(wifi):"
			"error in reading shell response\n");
			continue;
		}
		msg_len = rem_ptr->msg.len;
		error = rem_ptr->msg.cmd;
	} while (msg_len);

	rwl_shell_killproc(pid);
	return error;
}
Пример #18
0
/* This function will send the buffer to the dongle driver */
int
rwl_var_send_vs_actionframe(void* wl, const char* iovar, void* param, int param_len)
{
	int len;

	memset(rwl_buf, 0, WLC_IOCTL_MAXLEN);
	strcpy((char*) rwl_buf, iovar);

	/* include the null */
	len = strlen(iovar) + 1;

	if (param_len)
		memcpy((void*)&rwl_buf[len+ OFFSETOF(wl_action_frame_t, data)], param, param_len);

	/* Set the PacketID (not used by remote WL */
	memset((void*)&rwl_buf[len + OFFSETOF(wl_action_frame_t, packetId)], 0, 4);

	/* Set the dest addr */
	memcpy((void*)&rwl_buf[len + OFFSETOF(wl_action_frame_t, da)],
	(void*)&rwlea,
	ETHER_ADDR_LEN);

	/*  set the length */
	memcpy((void*)&rwl_buf[len + OFFSETOF(wl_action_frame_t, len)], (void*) &param_len, 2);

	len  += param_len + ETHER_ADDR_LEN + 2 + 4;

	DPRINT_DBG(OUTPUT, "setbuf:%s, len:%d\n", rwl_buf, len);

	return wl_set(wl, WLC_SET_VAR, &rwl_buf[0], len);
}
/*++

Name: 
	CopyToRingBuffer()

Description:
	Helper routine to copy from source to ring buffer.
	Assume there is enough room. Handles wrap-around in dest case only!!

--*/
UINT32
CopyToRingBuffer(
	RING_BUFFER_INFO	*RingInfo,	
	UINT32				StartWriteOffset, 
	PVOID				Src, 
	UINT32				SrcLen)
{
	/* Fixme:  This should not be a void pointer! */
	PVOID ringBuffer=GetRingBuffer(RingInfo); 
	UINT32 ringBufferSize=GetRingBufferSize(RingInfo); 
	UINT32 fragLen;

	if (SrcLen > ringBufferSize - StartWriteOffset) // wrap-around detected!
	{
		DPRINT_DBG(VMBUS, "wrap-around detected!");

		fragLen = ringBufferSize - StartWriteOffset;
		/* Fixme:  Cast needed due to void pointer */
		memcpy((UCHAR *)ringBuffer + StartWriteOffset, Src, fragLen);
		/* Fixme:  Cast needed due to void pointer */
		memcpy(ringBuffer, (UCHAR *)Src + fragLen, SrcLen - fragLen);
	}
	else
	{
		/* Fixme:  Cast needed due to void pointer */
		memcpy((unsigned char *)ringBuffer + StartWriteOffset, Src, SrcLen);
	}

	StartWriteOffset += SrcLen;
	StartWriteOffset %= ringBufferSize;

	return StartWriteOffset;
}
Пример #20
0
/*
 * Time Sync Channel message handler.
 */
static void timesync_onchannelcallback(void *context)
{
	struct vmbus_channel *channel = context;
	u32 recvlen;
	u64 requestid;
	struct icmsg_hdr *icmsghdrp;
	struct ictimesync_data *timedatap;

	vmbus_recvpacket(channel, time_txf_buf,
			 PAGE_SIZE, &recvlen, &requestid);

	if (recvlen > 0) {
		DPRINT_DBG(VMBUS, "timesync packet: recvlen=%d, requestid=%lld",
			recvlen, requestid);

		icmsghdrp = (struct icmsg_hdr *)&time_txf_buf[
				sizeof(struct vmbuspipe_hdr)];

		if (icmsghdrp->icmsgtype == ICMSGTYPE_NEGOTIATE) {
			prep_negotiate_resp(icmsghdrp, NULL, time_txf_buf);
		} else {
			timedatap = (struct ictimesync_data *)&time_txf_buf[
				sizeof(struct vmbuspipe_hdr) +
				sizeof(struct icmsg_hdr)];
			adj_guesttime(timedatap->parenttime, timedatap->flags);
		}

		icmsghdrp->icflags = ICMSGHDRFLAG_TRANSACTION
			| ICMSGHDRFLAG_RESPONSE;

		vmbus_sendpacket(channel, time_txf_buf,
				recvlen, requestid,
				VM_PKT_DATA_INBAND, 0);
	}
}
Пример #21
0
int
rwl_sockconnect(int SockDes, struct sockaddr *servAddr, int size)
{
	DPRINT_DBG(OUTPUT, "sockconnet SockDes=%d\n", SockDes);
	if (rwl_connectsocket(SockDes, servAddr, size) < 0) {
			DPRINT_ERR(ERR, "\n Server is not running\n");
			return FAIL;
	}
	return SUCCESS;
}
Пример #22
0
static int
rwl_opensocket(int AddrFamily, int Type, int Protocol)
{
	int SockDes;
	if ((SockDes = socket(AddrFamily, Type, Protocol)) == INVALID_SOCKET) {
		DPRINT_ERR(ERR, "\n rwl_opensocket Fails:%d\n", WSAGetLastError());
		return FAIL;
	}
	DPRINT_DBG(OUTPUT, "SockDes=%d\n", SockDes);
	return SockDes;

}
Пример #23
0
/*
 * Heartbeat functionality.
 * Every two seconds, Hyper-V send us a heartbeat request message.
 * we respond to this message, and Hyper-V knows we are alive.
 */
static void heartbeat_onchannelcallback(void *context)
{
	struct vmbus_channel *channel = context;
	u32 recvlen;
	u64 requestid;
	struct icmsg_hdr *icmsghdrp;
	struct heartbeat_msg_data *heartbeat_msg;

	vmbus_recvpacket(channel, hbeat_txf_buf,
			 PAGE_SIZE, &recvlen, &requestid);

	if (recvlen > 0) {
		DPRINT_DBG(VMBUS, "heartbeat packet: len=%d, requestid=%lld",
			   recvlen, requestid);

		icmsghdrp = (struct icmsg_hdr *)&hbeat_txf_buf[
				sizeof(struct vmbuspipe_hdr)];

		if (icmsghdrp->icmsgtype == ICMSGTYPE_NEGOTIATE) {
			prep_negotiate_resp(icmsghdrp, NULL, hbeat_txf_buf);
		} else {
			heartbeat_msg =
				(struct heartbeat_msg_data *)&hbeat_txf_buf[
					sizeof(struct vmbuspipe_hdr) +
					sizeof(struct icmsg_hdr)];

			DPRINT_DBG(VMBUS, "heartbeat seq = %lld",
				   heartbeat_msg->seq_num);

			heartbeat_msg->seq_num += 1;
		}

		icmsghdrp->icflags = ICMSGHDRFLAG_TRANSACTION
			| ICMSGHDRFLAG_RESPONSE;

		vmbus_sendpacket(channel, hbeat_txf_buf,
				       recvlen, requestid,
				       VM_PKT_DATA_INBAND, 0);
	}
}
Пример #24
0
rem_ioctl_t *
remote_CDC_rx_hdr(void *remote, int debug)
{
#ifdef RWL_SOCKET
	int ret;
#endif /* RWL_SOCKET */
	uint numread = 0;
	rem_ioctl_t *rem_ptr = &rem_cdc;
	memset(rem_ptr, 0, sizeof(rem_ioctl_t));

#ifdef RWL_WIFI
	UNUSED_PARAMETER(remote);
	UNUSED_PARAMETER(numread);
#endif /* RWL_WIFI */

	UNUSED_PARAMETER(debug);

	switch (remote_type)	{
#if defined(RWL_SERIAL) || defined(RWL_DONGLE)
		case REMOTE_SERIAL:
		case REMOTE_DONGLE:
			if (rwl_read_serial_port(remote, (char *)rem_ptr, sizeof(rem_ioctl_t),
				&numread) < 0) {
				DPRINT_ERR(ERR, "remote_CDC_rx_hdr: Header Read failed \n");
				return (NULL);
			}
			break;
#endif /* RWL_SERIAL |  RWL_DONGLE */


#ifdef RWL_SOCKET
		case REMOTE_SOCKET:
			ret = rwl_receive_from_streamsocket(*(int*)remote, (char *)rem_ptr,
				sizeof(rem_ioctl_t), 0);
			numread = ret;
			if (ret == -1) {
				DPRINT_ERR(ERR, "remote_CDC_rx_hdr: numread:%d", numread);
				return (NULL);
			}
		if (numread == 0) {
		      DPRINT_DBG(OUTPUT, "\n remote_CDC_rx_hdr:No data to receive\n");
			return NULL;
			}
			break;
#endif
		default:
			DPRINT_ERR(ERR, "\n Unknown Transport Type\n");
			break;
	}

	return (rem_ptr);
}
Пример #25
0
/* Make initial connection from client to server through sockets */
static int
rwl_connect_socket_server(void)
{
	int SockDes = -1;
	struct sockaddr_in servAddr;
	int retries = 0;
	int max_retries = 20;
	int connected = 0;

	memset(&servAddr, 0, sizeof(servAddr));

	while ((connected == 0) && (retries < max_retries)) {
		DPRINT_DBG(OUTPUT, "rwl_connect_socket_server retry %d\n", retries);
		if ((SockDes = (*(int *)rwl_open_pipe(remote_type, "\0", 0, 0))) == FAIL) {
			retries++;
			continue;
		}
		/*if (!validate_server_address()) {
			retries++;
			continue;
		}*/

		DPRINT_DBG(OUTPUT, "ServerIP:%s,ServerPort:%d\n", g_rwl_servIP, g_rwl_servport);
		servAddr.sin_family = AF_INET;
		servAddr.sin_port = hton16(g_rwl_servport);
		servAddr.sin_addr.s_addr = inet_addr(g_rwl_servIP);

		if (rwl_sockconnect(SockDes, (struct sockaddr *)&servAddr, sizeof(servAddr)) < 0) {
			rwl_close_pipe(remote_type, (void*) &SockDes);
			retries++;
			continue;
		} else
			connected = 1;
	}
	return SockDes;
}
Пример #26
0
int
rwl_read_serial_port(void* hndle, char* read_buf, uint data_size, uint *numread)
{
	uint total_numread = 0;
	int c = 0;

	while (total_numread < data_size) {
		if (ReadFile(hndle, read_buf, data_size - total_numread, (LPDWORD) numread, NULL) == 0) {
			DPRINT_ERR(ERR, "rwl_read_serial_port failed with:%d", GetLastError());
			return FAIL;
		}
		if (*numread != data_size - total_numread) {
			c++;
			DPRINT_DBG(OUTPUT, "asked %d bytes got %d bytes\n",
				data_size - total_numread, *numread);
			if (c > MAX_SERIAL_READ_RETRY) {
			        DPRINT_ERR(ERR, "rwl_read_serial_port failed: "
				           "reached max retry limit.\n");
				return FAIL;
			}
			Sleep(10);
		}

		total_numread += *numread;
		read_buf += *numread;
	}
#ifdef DEBUG_SERIAL
    printf( "\nr %04d < ", total_numread);
    int i;
    for( i = 0; i < total_numread; i++ )
    {
#ifdef READABLE_SERIAL_DUMP
        if ( ( orig_read_buf[i] >= 0x20 ) && ( orig_read_buf[i] <= 0x7E ) )
        {
            printf( "%c",orig_read_buf[i]);
        }
        else
        {
            printf( "\\x%02X",(unsigned char)orig_read_buf[i]);
        }
#else /* ifdef READABLE_SERIAL_DUMP */
        printf( " %02X",(unsigned char)orig_read_buf[i]);
#endif /* ifdef READABLE_SERIAL_DUMP */
    }
    printf("\n");
#endif /* ifdef DEBUG_SERIAL */
	return SUCCESS;
}
Пример #27
0
/* Function: rwl_transport_setup
 * This will do the initialization for
 * for all the transports
 */
static int
rwl_transport_setup(int argc, char** argv)
{
	int transport_descriptor = -1;

	UNUSED_PARAMETER(argc);
	UNUSED_PARAMETER(argv);

#ifdef RWL_SOCKET
	/* This function will parse the socket command line arguments
	 * & open the socket in listen mode
	 */
	remote_type = REMOTE_SOCKET;
	transport_descriptor = rwl_init_server_socket_setup(argc, argv, remote_type);

	if (transport_descriptor < 0) {
		DPRINT_ERR(ERR, "wl_socket_server:Transport setup failed \n");
	}
#endif /* RWL_SOCKET */
#if defined (RWL_DONGLE) || defined (RWL_WIFI) || defined (RWL_SERIAL)
	g_rem_pkt_ptr = &g_rem_pkt;
	transport_descriptor = 0;

#ifdef RWL_WIFI
	remote_type = REMOTE_WIFI;
#endif

#ifdef RWL_DONGLE
	remote_type = REMOTE_DONGLE;
#endif /* RWL_DONGLE */
#ifdef RWL_SERIAL
	remote_type = REMOTE_SERIAL;
	if (argc < 2) {
		DPRINT_ERR(ERR, "Port name is required from the command line\n");
	} else {
		(void)*argv++;
		DPRINT_DBG(OUTPUT, "Port name is %s\n", *argv);
		transport_descriptor = *(int*) rwl_open_transport(remote_type, *argv, 0, 0);
	}
#endif  /* RWL_SERIAL */
#endif /* RWL_DONGLE ||RWL_SERIAL ||RWL_WIFI */
#ifdef RWLASD
	g_serv_sock_desc = transport_descriptor;
#endif
	return transport_descriptor;

}
Пример #28
0
/* This routine is common to both set and Get Ioctls for the dongle case */
static int
rwl_information_dongle(void *wl, int cmd, void* input_buf, unsigned long *input_len,
	uint tx_len, uint flags)
{
	int error;
	rem_ioctl_t *rem_ptr = NULL;

	if (remote_CDC_tx(wl, cmd, input_buf, *input_len,
		tx_len, flags, 0) < 0) {
		DPRINT_ERR(ERR, "query_info_fe: Send command failed\n");
		return FAIL;
	}

	/* Get the header */
	if ((rem_ptr = remote_CDC_rx_hdr(wl, 0)) == NULL) {
		DPRINT_ERR(ERR, "query_info_fe: Reading CDC header failed\n");
		return SERIAL_PORT_ERR;
	}

	/* Make sure there is enough room */
	if (rem_ptr->msg.len > *input_len) {
		DPRINT_DBG(OUTPUT, "query_info_fe: needed size(%d) > actual"
			"size(%ld)\n", rem_ptr->msg.len, *input_len);
		return FAIL;
	}

	/*  We can grab short frames all at once.  Longer frames (> 960 bytes)
	 *  come in fragments.
	*/
	if (rem_ptr->data_len < DATA_FRAME_LEN) {
		if (remote_CDC_rx(wl, rem_ptr, input_buf, *input_len, 0) == FAIL) {
			DPRINT_ERR(ERR, "query_info_fe: No results!\n");
			return FAIL;
		}
		if (rem_ptr->msg.flags & REMOTE_REPLY)
			error = rem_ptr->msg.cmd;
		else
			error = 0;
	} else {
		/* rwl_serial_fragmented_response_fe returns either valid number or FAIL.
		  * In any case return the same value to caller
		*/
		error = rwl_serial_fragmented_response_fe(wl, rem_ptr, input_buf, input_len);
	}
	return error;
}
Пример #29
0
/**
 * VmbusInitialize - Main entry point
 */
int VmbusInitialize(struct hv_driver *drv)
{
	struct vmbus_driver *driver = (struct vmbus_driver *)drv;
	int ret;

	DPRINT_ENTER(VMBUS);

	DPRINT_INFO(VMBUS, "+++++++ Build Date=%s %s +++++++",
			VersionDate, VersionTime);
	DPRINT_INFO(VMBUS, "+++++++ Build Description=%s +++++++",
			VersionDesc);
	DPRINT_INFO(VMBUS, "+++++++ Vmbus supported version = %d +++++++",
			VMBUS_REVISION_NUMBER);
	DPRINT_INFO(VMBUS, "+++++++ Vmbus using SINT %d +++++++",
			VMBUS_MESSAGE_SINT);
	DPRINT_DBG(VMBUS, "sizeof(VMBUS_CHANNEL_PACKET_PAGE_BUFFER)=%zd, "
			"sizeof(VMBUS_CHANNEL_PACKET_MULITPAGE_BUFFER)=%zd",
			sizeof(struct VMBUS_CHANNEL_PACKET_PAGE_BUFFER),
			sizeof(struct VMBUS_CHANNEL_PACKET_MULITPAGE_BUFFER));

	drv->name = gDriverName;
	memcpy(&drv->deviceType, &gVmbusDeviceType, sizeof(struct hv_guid));

	/* Setup dispatch table */
	driver->Base.OnDeviceAdd	= VmbusOnDeviceAdd;
	driver->Base.OnDeviceRemove	= VmbusOnDeviceRemove;
	driver->Base.OnCleanup		= VmbusOnCleanup;
	driver->OnIsr			= VmbusOnISR;
	driver->OnMsgDpc		= VmbusOnMsgDPC;
	driver->OnEventDpc		= VmbusOnEventDPC;
	driver->GetChannelOffers	= VmbusGetChannelOffers;
	driver->GetChannelInterface	= VmbusGetChannelInterface;
	driver->GetChannelInfo		= VmbusGetChannelInfo;

	/* Hypervisor initialization...setup hypercall page..etc */
	ret = HvInit();
	if (ret != 0)
		DPRINT_ERR(VMBUS, "Unable to initialize the hypervisor - 0x%x",
				ret);
	gDriver = drv;

	DPRINT_EXIT(VMBUS);

	return ret;
}
Пример #30
0
/*
 * Time Sync Channel message handler.
 */
static void timesync_onchannelcallback(void *context)
{
	struct vmbus_channel *channel = context;
	u8 *buf;
	u32 buflen, recvlen;
	u64 requestid;
	struct icmsg_hdr *icmsghdrp;
	struct ictimesync_data *timedatap;

	DPRINT_ENTER(VMBUS);

	buflen = PAGE_SIZE;
	buf = kmalloc(buflen, GFP_ATOMIC);

	VmbusChannelRecvPacket(channel, buf, buflen, &recvlen, &requestid);

	if (recvlen > 0) {
		DPRINT_DBG(VMBUS, "timesync packet: recvlen=%d, requestid=%lld",
			recvlen, requestid);

		icmsghdrp = (struct icmsg_hdr *)&buf[
				sizeof(struct vmbuspipe_hdr)];

		if (icmsghdrp->icmsgtype == ICMSGTYPE_NEGOTIATE) {
			prep_negotiate_resp(icmsghdrp, NULL, buf);
		} else {
			timedatap = (struct ictimesync_data *)&buf[
				sizeof(struct vmbuspipe_hdr) +
				sizeof(struct icmsg_hdr)];
			adj_guesttime(timedatap->parenttime, timedatap->flags);
		}

		icmsghdrp->icflags = ICMSGHDRFLAG_TRANSACTION
			| ICMSGHDRFLAG_RESPONSE;

		VmbusChannelSendPacket(channel, buf,
				recvlen, requestid,
				VmbusPacketTypeDataInBand, 0);
	}

	kfree(buf);

	DPRINT_EXIT(VMBUS);
}