UNICODE_STRING 未初始化导致的崩溃

本文介绍了一个关于Windows驱动开发中出现蓝屏的问题及解决过程。问题出现在使用RtlUnicodeStringPrintf函数时,通过WinDbg调试发现是由于未正确初始化UNICODE_STRING变量导致。最终解决方案是使用RtlInitUnicodeString进行初始化。

上午还正常的驱动,下午改了些代码,运行突然就蓝屏了。


立刻用WINDBG看了CASH文件,大概确定是操作一个UNICODE_STRING变量导致的崩溃。


经过调试错误是发生在RtlUnicodeStringPrintf(&DestFile,L"%wsAY.DAT",dir);


解决办法:需要RtlInitUnicodeString初始化DestFile(UNICODE_STRING变量)

#include "custom_core.h" #define USBD_VID 0xABCDU #define USBD_PID 0x1234U /* USER */ extern rt_sem_t Sem_usb_rc; extern rt_sem_t Sem_usb_se; uint8_t custom_rc_buff[512]; uint8_t custom_se_buff[512]; extern usb_core_driver usbd_custom; /* USB standard device descriptor USB标准设备描述符 */ __ALIGN_BEGIN const usb_desc_dev custom_dev_desc __ALIGN_END = { .header = { .bLength = USB_DEV_DESC_LEN, //0x12 此描述表的字节数 18个 .bDescriptorType = USB_DESCTYPE_DEV, //描述符的类型 0x01 设备描述符 }, .bcdUSB = 0x0200U, //USB版本 USB2.0 则0x200 USB2.13 则0x213 .bDeviceClass = 0xFFU, // 设备为自定义设备类型 0xff .bDeviceSubClass = 0x00U, //子类掩码 保留 .bDeviceProtocol = 0x00U, //0x00 .bMaxPacketSize0 = USB_FS_EP0_MAX_LEN, //端点0的最大包大小64 .idVendor = USBD_VID, // 0xABCDU 厂商标志 .idProduct = USBD_PID, //0x1234U 产品标志 .bcdDevice = 0x0100U, //0x0100U 设备发行号 .iManufacturer = STR_IDX_MFC, //(uint8_t *)&manufacturer_string 描述厂商信息的字符串描述符的索引值 .iProduct = STR_IDX_PRODUCT, //(uint8_t *)&product_string 描述产品信息的字串描述符的索引值 .iSerialNumber = STR_IDX_SERIAL, //(uint8_t *)&serial_string 描述设备序列号信息的字串描述符的索引值 .bNumberConfigurations = USBD_CFG_MAX_NUM, //配置描述符数目 1 }; /* USB device configuration descriptor USB本设备的配置 */ __ALIGN_BEGIN const usb_custom_desc_config_set custom_config_desc __ALIGN_END = { .config = { .header = { .bLength = sizeof(usb_desc_config), .bDescriptorType = USB_DESCTYPE_CONFIG //0x02 配置描述符 }, .wTotalLength = USB_DEV_CONFIG_DESC_LEN, //此配置信息的总长(包括配置,接口,端点,设备类,厂商定义的描述符) .bNumInterfaces = 0x01U, //此配置的接口数量 .bConfigurationValue = 0x01U, //SetConfiguration()请求中用作参数选定此配置 .iConfiguration = 0x00U, //此配置的字串描述表索引 .bmAttributes = 0xD0U, // 自给电源 1101 .bMaxPower = 0x32U //耗电 (2*bMaxPower)mA }, .custom_itf = { .header = { .bLength = sizeof(usb_desc_itf), .bDescriptorType = USB_DESCTYPE_ITF //0x04 接口描述符 }, .bInterfaceNumber = 0x00U, //接口号 此接口配置索引值 .bAlternateSetting = 0x00U, //可选设置的索引值 .bNumEndpoints = 0x02U, //此接点用了几个端点 2个 .bInterfaceClass = 0x00U, //此接口类型 0x00 保留 0xff 厂商说明 .bInterfaceSubClass = 0x00U, //子类码 bInterfaceClass为0 则此必为0 .bInterfaceProtocol = 0x00U, //协议码 .iInterface = 0x00U //描述此接口的字串描述表的索引值 }, .custom_epin = { .header = { .bLength = sizeof(usb_desc_ep), .bDescriptorType = USB_DESCTYPE_EP //0x05 端点描述符 }, .bEndpointAddress = DEV_IN_EP, //端点地址与方向 0x81 地址为1的输入设备端点(设备到主机) .bmAttributes = USB_EP_ATTR_BULK, //USB_EP_ATTR_BULK 待验证 此端点的通道类型 0x2 批传送(块传送) .wMaxPacketSize = 512, //DEV_IN_PACKET 传送的块大小 512个字节 .bInterval = 0x00U //块传输,此位无意义 }, .custom_epout = { .header = { .bLength = sizeof(usb_desc_ep), .bDescriptorType = USB_DESCTYPE_EP //0x05 端点描述符 }, .bEndpointAddress = DEV_OUT_EP, //端点地址与方向 0x01 地址为1的输出设备端点(主机到设备) //地址是否可以重复使用待证实,端点单向,应该是不行,此地址需要更改 .bmAttributes = USB_EP_ATTR_BULK, //USB_EP_ATTR_BULK 块传送 .wMaxPacketSize = 512, //DEV_OUT_PACKET 传送的块大小 512个字节 .bInterval = 0x00U //块传输,此位无意义 }, }; /* USB language ID Descriptor USB语言ID描述符 */ static __ALIGN_BEGIN const usb_desc_LANGID usbd_language_id_desc __ALIGN_END = { .header = { .bLength = sizeof(usb_desc_LANGID), .bDescriptorType = USB_DESCTYPE_STR, // 0x03 字符串描述符 }, .wLANGID = ENG_LANGID //(uint8_t *)&usbd_language_id_desc 语言标识使用那一套编码 0x0409U english 0x0804U chinese }; /* USB manufacture string USB字符串描述符 */ static __ALIGN_BEGIN const usb_desc_str manufacturer_string __ALIGN_END = { .header = { .bLength = USB_STRING_LEN(10U), .bDescriptorType = USB_DESCTYPE_STR, }, .unicode_string = {'G', 'i', 'g', 'a', 'D', 'e', 'v', 'i', 'c', 'e'} }; /* USB product string USB字符串 */ static __ALIGN_BEGIN const usb_desc_str product_string __ALIGN_END = { .header = { .bLength = USB_STRING_LEN(20U), .bDescriptorType = USB_DESCTYPE_STR, }, .unicode_string = {'M', 'Y', ' ', 'U', 'S', 'B', ' ', 'B', 'u', 'l', 'k', ' ', 'T', 'r', 'a', 'n' , 's' , 'f' , 'e' ,'r'} }; /* USBD serial string USB串行字符串 */ static __ALIGN_BEGIN usb_desc_str serial_string __ALIGN_END = { .header = { .bLength = USB_STRING_LEN(12U), .bDescriptorType = USB_DESCTYPE_STR, } }; /* USB string descriptor USB字符串描述符 */ static void *const usbd_msc_strings[] = { [STR_IDX_LANGID] = (uint8_t *)&usbd_language_id_desc, [STR_IDX_MFC] = (uint8_t *)&manufacturer_string, [STR_IDX_PRODUCT] = (uint8_t *)&product_string, [STR_IDX_SERIAL] = (uint8_t *)&serial_string }; usb_desc custom_desc = { .dev_desc = (uint8_t *)&custom_dev_desc, .config_desc = (uint8_t *)&custom_config_desc, .strings = usbd_msc_strings }; /* local function prototypes ('static') 本地函数原型 静态*/ static uint8_t custom_init (usb_dev *udev, uint8_t config_index); static uint8_t custom_deinit (usb_dev *udev, uint8_t config_index); static uint8_t custom_req (usb_dev *udev, usb_req *req); static uint8_t custom_in (usb_dev *udev, uint8_t ep_num); static uint8_t custom_out (usb_dev *udev, uint8_t ep_num); usb_class_core usbd_custom_cb = { .init = custom_init, .deinit = custom_deinit, .req_proc = custom_req, .data_in = custom_in, .data_out = custom_out }; /*! \brief initialize the custom device 初始化自定义设备 \param[in] udev: pointer to USB device instance 指向USB设备实例的指针 \param[in] config_index: configuration index 配置索引 \param[out] none 无 \retval USB device operation status 返回USB操作状态 */ static uint8_t custom_init (usb_dev *udev, uint8_t config_index) { /* initialize the data TX endpoint */ usbd_ep_setup (udev, &(custom_config_desc.custom_epin)); /* initialize the data RX endpoint */ usbd_ep_setup (udev, &(custom_config_desc.custom_epout)); /* prepare to receive data */ usbd_ep_recev(udev, DEV_OUT_EP, custom_rc_buff, 512); return USBD_OK; } /*! \brief deinitialize the custom device 消除初始化自定义设备 \param[in] udev: pointer to USB device instance \param[in] config_index: configuration index \param[out] none \retval USB device operation status */ static uint8_t custom_deinit (usb_dev *udev, uint8_t config_index) { /* deinitialize the data TX/RX endpoint */ usbd_ep_clear (udev, DEV_IN_EP); usbd_ep_clear (udev, DEV_OUT_EP); return USBD_OK; } /*! \brief handle the custom class-specific requests 处理自定义类特定的请求 \param[in] udev: pointer to USB device instance \param[in] req: device class-specific request \param[out] none \retval USB device operation status */ static uint8_t custom_req(usb_dev *udev, usb_req *req) { return USBD_OK; } /*! \brief handle custom data 处理自定义设备数据 GD发送数据 \param[in] udev: pointer to USB device instance \param[in] ep_num: endpoint number \param[out] none \retval USB device operation status */ static uint8_t custom_in (usb_dev *udev, uint8_t ep_num) { rt_sem_release(Sem_usb_se); return USBD_OK; } /*! \brief handle printer data 处理自定义设备数据 GD接收数据 以中断方式接收 这里是回调函数 \param[in] udev: pointer to USB device instance \param[in] ep_num: endpoint number \param[out] none \retval USB device operation status */ static uint8_t custom_out (usb_dev *udev, uint8_t ep_num) /* OUT端回调函数,接收到数据之后会进入此函数 */ { rt_sem_release(Sem_usb_rc); return USBD_OK; } void usb_start_next_receive(void) { /* prepare to receive data */ usbd_ep_recev(&usbd_custom, DEV_OUT_EP, custom_rc_buff, 512); } rt_err_t usb_start_send(uint8_t *pbuf, uint32_t len) { rt_err_t err = RT_EOK; usbd_ep_send (&usbd_custom, DEV_IN_EP, pbuf, len); err = rt_sem_take(Sem_usb_se, 20); return err; }
最新发布
09-23
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值