⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ndis.c

📁 ndis在linux下的无线网卡驱动源码
💻 C
📖 第 1 页 / 共 5 页
字号:
		*param = NULL;		*status = NDIS_STATUS_FAILURE;		RtlFreeAnsiString(&ansi);		EXIT2(return);	}	TRACE3("%d, %s", type, ansi.buf);	keyname = ansi.buf;	if (read_setting(&nmb->wnd->wd->settings, keyname,			 ansi.length, param, type) == 0 ||	    read_setting(&nmb->wnd->wd->driver->settings, keyname,			 ansi.length, param, type) == 0)		*status = NDIS_STATUS_SUCCESS;	else {		TRACE2("setting %s not found (type:%d)", keyname, type);		*status = NDIS_STATUS_FAILURE;	}	RtlFreeAnsiString(&ansi);	EXIT2(return);}wstdcall void WIN_FUNC(NdisWriteConfiguration,4)	(NDIS_STATUS *status, struct ndis_miniport_block *nmb,	 struct unicode_string *key, struct ndis_configuration_parameter *param){	struct ansi_string ansi;	char *keyname;	struct wrap_device_setting *setting;	ENTER2("nmb: %p", nmb);	if (RtlUnicodeStringToAnsiString(&ansi, key, TRUE)) {		*status = NDIS_STATUS_FAILURE;		EXIT2(return);	}	keyname = ansi.buf;	TRACE2("%s", keyname);	if (down_interruptible(&loader_mutex))		WARNING("couldn't obtain loader_mutex");	nt_list_for_each_entry(setting, &nmb->wnd->wd->settings, list) {		if (strnicmp(keyname, setting->name, ansi.length) == 0) {			up(&loader_mutex);			if (ndis_decode_setting(setting, param))				*status = NDIS_STATUS_FAILURE;			else				*status = NDIS_STATUS_SUCCESS;			RtlFreeAnsiString(&ansi);			EXIT2(return);		}	}	up(&loader_mutex);	setting = kmalloc(sizeof(*setting), GFP_KERNEL);	if (setting) {		memset(setting, 0, sizeof(*setting));		if (ansi.length == ansi.max_length)			ansi.length--;		memcpy(setting->name, keyname, ansi.length);		setting->name[ansi.length] = 0;		if (ndis_decode_setting(setting, param))			*status = NDIS_STATUS_FAILURE;		else {			*status = NDIS_STATUS_SUCCESS;			if (down_interruptible(&loader_mutex))				WARNING("couldn't obtain loader_mutex");			InsertTailList(&nmb->wnd->wd->settings, &setting->list);			up(&loader_mutex);		}	} else		*status = NDIS_STATUS_RESOURCES;	RtlFreeAnsiString(&ansi);	EXIT2(return);}wstdcall void WIN_FUNC(NdisInitializeString,2)	(struct unicode_string *dest, UCHAR *src){	struct ansi_string ansi;	ENTER2("");	if (src == NULL) {		dest->length = dest->max_length = 0;		dest->buf = NULL;	} else {		RtlInitAnsiString(&ansi, src);		RtlAnsiStringToUnicodeString(dest, &ansi, TRUE);	}	EXIT2(return);}wstdcall void WIN_FUNC(NdisInitAnsiString,2)	(struct ansi_string *dst, CHAR *src){	RtlInitAnsiString(dst, src);	EXIT2(return);}wstdcall void WIN_FUNC(NdisInitUnicodeString,2)	(struct unicode_string *dest, const wchar_t *src){	RtlInitUnicodeString(dest, src);	return;}wstdcall NDIS_STATUS WIN_FUNC(NdisAnsiStringToUnicodeString,2)	(struct unicode_string *dst, struct ansi_string *src){	ENTER2("");	if (dst == NULL || src == NULL)		EXIT2(return NDIS_STATUS_FAILURE);	if (RtlAnsiStringToUnicodeString(dst, src, FALSE) == STATUS_SUCCESS)		return NDIS_STATUS_SUCCESS;	else		return NDIS_STATUS_FAILURE;}wstdcall NDIS_STATUS WIN_FUNC(NdisUnicodeStringToAnsiString,2)	(struct ansi_string *dst, struct unicode_string *src){	ENTER2("");	if (dst == NULL || src == NULL)		EXIT2(return NDIS_STATUS_FAILURE);	if (RtlUnicodeStringToAnsiString(dst, src, FALSE) == STATUS_SUCCESS)		return NDIS_STATUS_SUCCESS;	else		return NDIS_STATUS_FAILURE;}wstdcall void WIN_FUNC(NdisMSetAttributesEx,5)	(struct ndis_miniport_block *nmb, void *adapter_ctx,	 UINT hangcheck_interval, UINT attributes, ULONG adaptortype){	struct wrap_ndis_device *wnd;	ENTER1("%p, %p %d %08x, %d", nmb, adapter_ctx,	       hangcheck_interval, attributes, adaptortype);	wnd = nmb->wnd;	nmb->adapter_ctx = adapter_ctx;	wnd->attributes = attributes;	if ((attributes & NDIS_ATTRIBUTE_BUS_MASTER) &&	    wrap_is_pci_bus(wnd->wd->dev_bus))		pci_set_master(wnd->wd->pci.pdev);	if (hangcheck_interval > 0)		wnd->hangcheck_interval = 2 * hangcheck_interval * HZ;	else		wnd->hangcheck_interval = 2 * HZ;	EXIT1(return);}wstdcall ULONG WIN_FUNC(NdisReadPciSlotInformation,5)	(struct ndis_miniport_block *nmb, ULONG slot,	 ULONG offset, char *buf, ULONG len){	struct wrap_device *wd = nmb->wnd->wd;	ULONG i;	for (i = 0; i < len; i++)		if (pci_read_config_byte(wd->pci.pdev, offset + i, &buf[i]) !=		    PCIBIOS_SUCCESSFUL)			break;	DBG_BLOCK(2) {		if (i != len)			WARNING("%u, %u", i, len);	}	return i;}wstdcall ULONG WIN_FUNC(NdisImmediateReadPciSlotInformation,5)	(struct ndis_miniport_block *nmb, ULONG slot,	 ULONG offset, char *buf, ULONG len){	return NdisReadPciSlotInformation(nmb, slot, offset, buf, len);}wstdcall ULONG WIN_FUNC(NdisWritePciSlotInformation,5)	(struct ndis_miniport_block *nmb, ULONG slot,	 ULONG offset, char *buf, ULONG len){	struct wrap_device *wd = nmb->wnd->wd;	ULONG i;	for (i = 0; i < len; i++)		if (pci_write_config_byte(wd->pci.pdev, offset + i, buf[i]) !=		    PCIBIOS_SUCCESSFUL)			break;	DBG_BLOCK(2) {		if (i != len)			WARNING("%u, %u", i, len);	}	return i;}wstdcall void WIN_FUNC(NdisReadPortUchar,3)	(struct ndis_miniport_block *nmb, ULONG port, char *data){	*data = inb(port);}wstdcall void WIN_FUNC(NdisImmediateReadPortUchar,3)	(struct ndis_miniport_block *nmb, ULONG port, char *data){	*data = inb(port);}wstdcall void WIN_FUNC(NdisWritePortUchar,3)	(struct ndis_miniport_block *nmb, ULONG port, char data){	outb(data, port);}wstdcall void WIN_FUNC(NdisImmediateWritePortUchar,3)	(struct ndis_miniport_block *nmb, ULONG port, char data){	outb(data, port);}wstdcall void WIN_FUNC(NdisMQueryAdapterResources,4)	(NDIS_STATUS *status, struct ndis_miniport_block *nmb,	 NDIS_RESOURCE_LIST *resource_list, UINT *size){	struct wrap_ndis_device *wnd = nmb->wnd;	NDIS_RESOURCE_LIST *list;	UINT resource_length;	list = &wnd->wd->resource_list->list->partial_resource_list;	resource_length = sizeof(struct cm_partial_resource_list) +		sizeof(struct cm_partial_resource_descriptor) *		(list->count - 1);	TRACE2("%p, %p,%d (%d), %p %d %d", wnd, resource_list, *size,	       resource_length, &list->partial_descriptors[list->count-1],	       list->partial_descriptors[list->count-1].u.interrupt.level,	       list->partial_descriptors[list->count-1].u.interrupt.vector);	if (*size < sizeof(*list)) {		*size = resource_length;		*status = NDIS_STATUS_BUFFER_TOO_SHORT;	} else {		ULONG count;		if (*size >= resource_length) {			*size = resource_length;			count = list->count;		} else {			UINT n = sizeof(*list);			count = 1;			while (count++ < list->count && n < *size)				n += sizeof(list->partial_descriptors);			*size = n;		}		memcpy(resource_list, list, *size);		resource_list->count = count;		*status = NDIS_STATUS_SUCCESS;	}	EXIT2(return);}wstdcall NDIS_STATUS WIN_FUNC(NdisMPciAssignResources,3)	(struct ndis_miniport_block *nmb, ULONG slot_number,	 NDIS_RESOURCE_LIST **resources){	struct wrap_ndis_device *wnd = nmb->wnd;	ENTER2("%p, %p", wnd, wnd->wd->resource_list);	*resources = &wnd->wd->resource_list->list->partial_resource_list;	EXIT2(return NDIS_STATUS_SUCCESS);}wstdcall NDIS_STATUS WIN_FUNC(NdisMMapIoSpace,4)	(void **virt, struct ndis_miniport_block *nmb,	 NDIS_PHY_ADDRESS phy_addr, UINT len){	struct wrap_ndis_device *wnd = nmb->wnd;	ENTER2("%Lx, %d", phy_addr, len);	*virt = MmMapIoSpace(phy_addr, len, MmCached);	if (*virt == NULL) {		ERROR("ioremap failed");		EXIT2(return NDIS_STATUS_FAILURE);	}	wnd->mem_start = phy_addr;	wnd->mem_end = phy_addr + len;	TRACE2("%p", *virt);	EXIT2(return NDIS_STATUS_SUCCESS);}wstdcall void WIN_FUNC(NdisMUnmapIoSpace,3)	(struct ndis_miniport_block *nmb, void *virt, UINT len){	ENTER2("%p, %d", virt, len);	MmUnmapIoSpace(virt, len);	EXIT2(return);}wstdcall void WIN_FUNC(NdisAllocateSpinLock,1)	(struct ndis_spinlock *lock){	TRACE4("lock %p, %lu", lock, lock->klock);	KeInitializeSpinLock(&lock->klock);	lock->irql = PASSIVE_LEVEL;	EXIT4(return);}wstdcall void WIN_FUNC(NdisFreeSpinLock,1)	(struct ndis_spinlock *lock){	TRACE4("lock %p, %lu", lock, lock->klock);	EXIT4(return);}wstdcall void WIN_FUNC(NdisAcquireSpinLock,1)	(struct ndis_spinlock *lock){	TRACE6("lock %p, %lu", lock, lock->klock);	lock->irql = nt_spin_lock_irql(&lock->klock, DISPATCH_LEVEL);	EXIT6(return);}wstdcall void WIN_FUNC(NdisReleaseSpinLock,1)	(struct ndis_spinlock *lock){	TRACE6("lock %p, %lu", lock, lock->klock);	nt_spin_unlock_irql(&lock->klock, lock->irql);	EXIT6(return);}wstdcall void WIN_FUNC(NdisDprAcquireSpinLock,1)	(struct ndis_spinlock *lock){	ENTER6("lock %p", lock);	nt_spin_lock(&lock->klock);	EXIT6(return);}wstdcall void WIN_FUNC(NdisDprReleaseSpinLock,1)	(struct ndis_spinlock *lock){	ENTER6("lock %p", lock);	nt_spin_unlock(&lock->klock);	EXIT6(return);}wstdcall void WIN_FUNC(NdisInitializeReadWriteLock,1)	(struct ndis_rw_lock *rw_lock){	ENTER3("%p", rw_lock);	memset(rw_lock, 0, sizeof(*rw_lock));	KeInitializeSpinLock(&rw_lock->klock);	EXIT3(return);}/* read/write locks are implemented in a rather simplisitic way - we * should probably use Linux's rw_lock implementation */wstdcall void WIN_FUNC(NdisAcquireReadWriteLock,3)	(struct ndis_rw_lock *rw_lock, BOOLEAN write,	 struct lock_state *lock_state){	if (write) {		while (1) {			if (cmpxchg(&rw_lock->count, 0, -1) == 0)				return;			while (rw_lock->count)				cpu_relax();		}		return;	}	while (1) {		typeof(rw_lock->count) count;		while ((count = rw_lock->count) < 0)			cpu_relax();		if (cmpxchg(&rw_lock->count, count, count + 1) == count)			return;	}}wstdcall void WIN_FUNC(NdisReleaseReadWriteLock,2)	(struct ndis_rw_lock *rw_lock, struct lock_state *lock_state){	if (rw_lock->count > 0)		pre_atomic_add(rw_lock->count, -1);	else if (rw_lock->count == -1)		rw_lock->count = 0;	else		WARNING("invalid state: %d", rw_lock->count);}wstdcall NDIS_STATUS WIN_FUNC(NdisMAllocateMapRegisters,5)	(struct ndis_miniport_block *nmb, UINT dmachan,	 NDIS_DMA_SIZE dmasize, ULONG basemap, ULONG max_buf_size){	struct wrap_ndis_device *wnd = nmb->wnd;	ENTER2("%p, %d %d %d %d", wnd, dmachan, dmasize, basemap, max_buf_size);	if (wnd->dma_map_count > 0) {		WARNING("%s: map registers already allocated: %u",			wnd->net_dev->name, wnd->dma_map_count);		EXIT2(return NDIS_STATUS_RESOURCES);	}	/* since memory for buffer is allocated with kmalloc, buffer	 * is physically contiguous, so entire map will fit in one	 * register */	if (basemap > 64) {		WARNING("Windows driver %s requesting too many (%u) "			"map registers", wnd->wd->driver->name, basemap);		/* As per NDIS, NDIS_STATUS_RESOURCES should be		 * returned, but with that Atheros PCI driver fails -		 * for now tolerate it *///		EXIT2(return NDIS_STATUS_RESOURCES);	}	wnd->dma_map_addr = kmalloc(basemap * sizeof(*(wnd->dma_map_addr)),				    GFP_KERNEL);	if (!wnd->dma_map_addr)		EXIT2(return NDIS_STATUS_RESOURCES);	memset(wnd->dma_map_addr, 0, basemap * sizeof(*(wnd->dma_map_addr)));	wnd->dma_map_count = basemap;	TRACE2("%u", wnd->dma_map_count);	EXIT2(return NDIS_STATUS_SUCCESS);}wstdcall void WIN_FUNC(NdisMFreeMapRegisters,1)	(struct ndis_miniport_block *nmb){	struct wrap_ndis_device *wnd = nmb->wnd;	int i;	ENTER2("wnd: %p", wnd);	if (wnd->dma_map_addr) {		for (i = 0; i < wnd->dma_map_count; i++) {			if (wnd->dma_map_addr[i])				WARNING("%s: dma addr %p not freed by "					"Windows driver", wnd->net_dev->name,					(void *)wnd->dma_map_addr[i]);		}		kfree(wnd->dma_map_addr);		wnd->dma_map_addr = NULL;	} else		WARNING("map registers already freed?");	wnd->dma_map_count = 0;	EXIT2(return);}wstdcall void WIN_FUNC(NdisMStartBufferPhysicalMapping,6)	(struct ndis_miniport_block *nmb, ndis_buffer *buf,	 ULONG index, BOOLEAN write_to_dev,	 struct ndis_phy_addr_unit *phy_addr_array, UINT *array_size){	struct wrap_ndis_device *wnd = nmb->wnd;	ENTER3("%p, %p, %u, %u", wnd, buf, index, wnd->dma_map_count);	if (unlikely(wnd->sg_dma_size || !write_to_dev ||		     index >= wnd->dma_map_count)) {		WARNING("invalid request: %d, %d, %d, %d", wnd->sg_dma_size,			write_to_dev, index, wnd->dma_map_count);		phy_addr_array[0].phy_addr = 0;		phy_addr_array[0].length = 0;		*array_size = 0;		return;	}	if (wnd->dma_map_addr[index]) {		TRACE2("buffer %p at %d is already mapped: %lx", buf, index,		       (unsigned long)wnd->dma_map_addr[index]);//		*array_size = 1;		return;	}	TRACE3("%p, %p, %u", buf, MmGetSystemAddressForMdl(buf),

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -