50
Running head: Developing a Windows Driver for the PIC Microcontroller 1 Developing a Windows Uniform Serial Bus Driver for the PIC Microcontroller John H. Dunbar LIB-495 Liberal Arts Capstone Section Number OL011 Thomas Edison State College Mentor: Dr. Augustus Black October 2016

PICDriverResearch

Embed Size (px)

Citation preview

Page 1: PICDriverResearch

Running head: Developing a Windows Driver for the PIC Microcontroller 1

Developing a Windows Uniform Serial Bus Driver for the PIC Microcontroller

John H. Dunbar

LIB-495 Liberal Arts Capstone

Section Number OL011

Thomas Edison State College

Mentor: Dr. Augustus Black

October 2016

Page 2: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 2

Abstract

Computer users need methods to access the information stored on a computer and interact with

the computer in useful ways. A microcontroller is an integrated electronic circuit which can

convert user interaction into electronic signals. A driver can be written for an operating system to

convert the electronic signals from the microcontroller into instructions for the computer.

Keywords: driver, operating system, microcontroller

Page 3: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 3

Developing a Windows Uniform Serial Bus Driver for the PIC Microcontroller

Chapter 1: Introduction

Introduction to the Chapter

Advanced integrated circuits exist which allow custom computer hardware interfaces to

be created. These interfaces require complex software known as drivers to be recognized by and

communicate with a computer. Hardware interfaces come in many varieties including Peripheral

Component Interconnect (PCI), Universal Serial Bus (USB), and serial. Similarly, there are a

variety of computer operating systems which communicate with hardware interfaces using

different programming languages. There are many combinations of microcontrollers, operating

systems, and interface types. This study aims to identify the basic requirements to develop a

Windows USB driver for a PIC18F45K50 microcontroller.

Background of the Topic

Advances in computer peripheral technology appear to be happening at a rapid rate.

Oculus just came out with a virtual reality headset. Microsoft will soon be selling the augmented

reality HoloLens. TrackIR has developed a sensor to capture head motion on translate it to in

game character’s head motion (NaturalPoint Inc., 2016). These are all devices that have come

about in the last few years that will shape the way that we interact with computers and they all

utilize USB connectivity.

Problem Statement

There are two microcontrollers in existence which are identified as USB devices by the

computer. One is the Arduino. The Arduino is a cheap easy to use board with a lot of online help

and documentation. However, this board isn’t designed to be programmed as a computer

Page 4: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 4

peripheral. It is designed to act as a stand-alone device that can be used to run household projects

like an aquaponics system or Christmas lights. The second microcontroller is called the Teensy.

The Teensy can be programmed as a keyboard, a mouse, joystick, or game pad and it already has

drivers written for it. The problem with the Teensy is that the premade drivers are generic. For

example, the mouse driver is only programmed to have left click, right click, middle click,

mouse wheel, and x/y position. That does in fact describe a fully functional mouse. However,

what it doesn’t give you is the ability to add new features or take away unnecessary features.

This issue led me to find a microcontroller that would offer potential for customization

and to the major research question: How to write a Windows USB driver for the PIC

microcontroller?

To do that, I first must discover: What is a driver? What are the hardware requirements

for a USB device? How does a computer communicate with a USB device? Will the internal

clock on the PIC be fast enough for USB communication? Do I need an external clock? What is

the difference between a driver for Windows compared to other operating systems? How are

drivers for a USB device different from those of a PCI device?

Professional Significance of Work

Computers are powerful resources which people use daily to perform a variety of tasks

from ordering lunch to performing advanced scientific research. In the 1980’s when computers

were just becoming mainstream peripheral devices included mainly the key board and mouse.

Now there are printers, 3D printers, virtual reality, augmented reality, facial recognition, game

controllers, and more. The ability to develop custom peripheral computer hardware is a powerful

tool for an information technology professional to have.

Page 5: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 5

Software developers have a challenging time creating products that are compatible with

the large variety of hardware and operating system combinations in existence. Hardware drivers

can be developed to function on multiple operating systems. From an economic standpoint, if

resources are limited, it is better to develop a driver for the Window’s operating system because

it has an over 80% market share among desktop computers ( Net Applications.com, 2006-2016).

Also, because it is such a common operating system, the amount of documentation and support

provided to developers is much greater.

In a similar way, because USB is such a commonly used hardware connection type, it

makes sense that it should be a priority when learning to write Window’s drivers. One could also

learn to write drivers for PCI or serial devices. However, they are less common, more complex,

and don’t have as much support and documentation as USB.

Overview of Methodology

To write a driver, first a device is needed. This is where the PIC microcontroller comes

into play. The microcontroller will act as the brain to which connects the other components of the

controller. The PIC18F45K50 is a good choice because it is USB compatible and has the

capability to connect up to 33 switches (Microchip Technology Inc., 2012-2014), giving potential

to create more in depth projects.

An entire test circuit will be set up on a breadboard to save on the time and cost of

purchasing and designing a custom circuit board. The PIC comes with blank memory. To write

code to the chip, a Cana Kit programmer was acquired. Microcontroller program code will be

written using the MPLAB Integrated Development Environment (IDE). The code will then be

translated to hexadecimal by MPLAB and subsequently written to the chip utilizing the Cana Kit

programmer and the PIC Kit 2 software.

Page 6: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 6

To test the validity of the development environment, a simple LED blink program will be

written to the PIC microcontroller. The microcontroller will then be then inserted into the

breadboard and wired to the LED. Once power is applied to the microcontroller and the LED

blinks, the development environment will have been proven to work. The next step is to write a

simple driver that can write to the LED pin and toggle the LED on or off. The driver for

Windows will be written in C# utilizing the Microsoft Visual Studio IDE. Documentation on the

Microsoft website will be utilized to ensure that Microsoft standards for USB communication are

followed. Once the simple driver is created, the capability of the driver could potentially be

expanded for a large variety inputs and outputs.

Delimitations

It would be interesting to test the device to see if driver profiles could be set up to specify

different hardware configurations in the microcontroller. This would allow users to quickly

change the way the computer sees a device. A game controller could end up being used as a

mouse or a keyboard by using a separate profile. However, due to the time constraints of the

research, testing will be saved for a later time.

Definition of Terms

Driver- software designed by electronics manufacturers to allow peripheral

devices to communicate with an operating system

Microcontroller- a programmable electronic chip used for embedded electronics

Universal Serial Bus (USB)- a type of connection to a computer used commonly

today to connect to and share data with a computer from devices not directly

connected to the motherboard

Page 7: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 7

Peripheral Component Interconnect (PCI)- the type of connections on a

computer motherboard commonly used for connecting peripherals such as

graphics cards or network cards

Integrated Programming Environment (IDE)- a computer program which

includes features and tools for writing other computer programs

Breadboard- a device made of a matrix of conductive material used for creating

prototype electronic circuits without the need for soldering

Summary

There are many ways for peripheral devices to communicate with a computer. The most flexible

method of communication is USB. There are existing microcontrollers to communicate with the

PC however, they only offer limited capabilities. It would be convenient and professionally

rewarding to create custom USB drivers.

Chapter 2: Literature Review

Introduction

There is a distinct path that data follows as it passes from the device to the host. A review

of the literature shows that starting from a USB device, a microcontroller is required to pass data

on to the host (Axelson, 2015, pg. 25). Once data is generated on a device, it travels across the

USB cable and through the connectors to the host. For proper communication to occur, the host

must know what type of data to expect (Axelson, 2015, pg. 95-96). This is accomplished through

enumeration and the creation of pipes using a devices endpoint descriptor (Axelson, 2015, pg.

95-96). At this point, the driver takes control and shuffles data between applications and the

device (Orwick & Smith, 2007, Chap. 5, para. 1).

Body Paragraphs

Page 8: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 8

PIC Microcontroller

In his book, Designing Embedded Hardware, Catsoulis (2005) explains how in the 1970’s the

company General Instruments manufactured a 16-bit processor called the CP1600. The company

began to suffer because Intel and Motorola were building competing processors with greater I/O

capability. As a solution to the CP1600’s limited I/O capability, General Instruments developed a

Peripheral Interface Controller (PIC) to boost the I/O of the CP1600. In the end, General

Instruments lost to Intel and Motorola. However, the PIC processor continues to be manufactured

by the company Microchip Technology which was created from the microelectronics division of

General Instruments (Chap. 14 2nd paragraph). PIC microcontrollers are popular because they are

cheap, readily available, include many varieties of chips, and don’t consume very much power

(Axelson, 2015, p. 153). The PIC microcontroller is so common that it can be found in Sony

PlayStation hand controllers, children’s toys, consumer appliances, and industrial systems

(Catsoulis, 2005, Chap. 14 2nd paragraph). Another application of PIC microcontrollers is

controlling USB device communications. For a USB device to connect to a host it needs a USB

compatible chip with a CPU or other architecture for exchanging data with a host (Axelson,

2015, p. 25). All microcontrollers include a CPU, memory, and I/O connections on a chip

(Rafiquzzaman, 2014, Chap. 7 3rd paragraph). However, not all microcontrollers are built for

USB communication. The PIC is one brand of microcontroller with models capable of USB

device control. The PIC18F45K50 is a specific model of microcontroller that is capable of USB

communication. (28/40/44-Pin, 2014, p. 1).

USB Specifications

There are several versions of USB which can be used for passing data from a device to a

host. In a white paper written by Murphy (2016), he describes the various versions of USB,

Page 9: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 9

saying, in 1996 USB 1.0 was introduced. It supported a low speed connection of 1.5Mb/s and a

full speed connection of 12Mb/s. High speed transmission can be a problem because it causes a

buildup of electromagnetic interference (EMI) which requires more expensive manufacturing

materials to mitigate. Having two speeds is beneficial because it allows manufacturers who don’t

require high speed data transmission to use cheaper parts. In 1998 USB 1.1 was developed to add

some minor improvements to the 1.0 specification (p. 2). In 2000, USB 2.0 was released with a

new high speed transfer rate of 480 Mb/s (USB-IF, 2000, p. 11). USB 3.0 was released in 2008

and brought the maximum transfer speed up to 5 Gb/s, more than 10 times the speed of USB 2.0

(USB-IF, 2011, p. 3-5). The latest version of USB is 3.1. It was released in 2013 and includes

new power saving features and a 10 Gb/s transfer rate (USB-IF, 2013, p. 1-1).

USB Physical Connection

Before data can be passed from device to host, a physical connection must be made

between the two. Axelson (2015) details the requirements of a USB 2.0 connection by stating

that connections are made with one wire for power, another for ground, and two signal wires

called D+ and D-. The predecessor to USB, called RS-232, used one signal wire for transmit and

the other for receive. USB uses both signal wires as either transmit or receive, restricting traffic

to one direction at a given time (p. 453). The USB 2.0 Specification (2008) describes the unique

USB connectors that can be used to terminate the two ends of the four-wire cable. The host end

(upstream) is terminated with a Series “A” connector. The device end (downstream) of the cable

utilizes Series “B” connector. However, manufacturers may opt to connect the cable directly to

the device without using a downstream connector (p. 86).

Page 10: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 10

(USB-IF, 2000, p. 87)

According to Catsoulis (2005), the entire USB system consists of at least one USB device

(with a maximum of 127), at least one hub, and one host. Although peripheral USB hubs exist,

the host possesses a root hub which serves as the origin for attached devices. A peripheral USB

hub is only required when the host lacks the number USB ports required for the number of

devices desired. A hub is required to allow the host to initiate communication with a device. This

initial communication is called enumeration (Chap. 11 para. 6 & 7).

USB Logical Connection

Transfer Types

Axelson (2015) describes four transfer types supported by USB devices. When a device

is connected to a host, the host uses control transfers to get device descriptors containing

information about the device capabilities. Bulk transfers are the fastest type of transfer but

cannot guarantee the integrity of data at the receiving end. Interrupt transfers are a transfer type

with a set maximum time to transfer. Isochronous transfers strictly follow standards of timing but

cannot handle error correcting (p. 34).

End Points

According to McDowell & Seyer (1998) an endpoint is a place defined within the

firmware of a USB device to which data can flow to or from. An endpoint can be either an input

Page 11: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 11

or an output but not both. For a USB device to receive both input and output, it needs at least two

endpoints (Chap. 2, What are Pipes and Endpoints, para. 2).

Axelson (2015) explains that an endpoint is a reserved block of memory in a device that is used

to hold a buffer that can store multiple incoming or outgoing bytes of information. Not including

endpoint zero, a high-speed device can have up to 30 endpoints (p. 36). Device firmware

declares the number of endpoints supported for a device and the details of how the device

expects to handle input and output on those endpoints. A review of the software library provided

by Microchip Technology shows that an endpoint descriptor transfer type is defined in the USB

endpoint descriptor (usb_descriptors.c, 2016).

Pipes

A logical connection between a host and a device is created with pipes that are matched

to endpoints. The Microsoft Developer Network website states that when the device is

configured, the driver assigns a pipe to the device endpoints defined in the descriptor. Depending

on the endpoint’s definition, the driver will pair it with a particular variety of pipe. A bulk

endpoint gets a bulk pipe, isochronous gets isochronous, interrupt gets interrupt, control gets

control (How to Enumerate USB Pipes, 2016, 3rd para.). McDowell & Seyer (1998) describe

two main categories of pipes which the four pipes discussed above fall under, stream pipes and

message pipes. Stream pipes have no predefined packet structure to abide by. Message pipes

have a structure dictated by the host and the data must be properly organized prior to

transmission. A control pipe (pipe zero) is used for device set up and transmission of data

describing device features. One control pipe exists for each device on a host (Chap. 2, What are

Pipes and Endpoints, para. 3). For data transfers to occur, Axelson (2015) states that a host is

Page 12: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 12

required to open a pipe to a device. Pipes are created when a device is connected to the host and

enumeration takes place. When the device is detached, pipes are destroyed (p. 37).

Enumeration/PnP Manager

Axelson (2015) describes that when a device is plugged into a USB port on a host, it

registers with the host through the enumeration process. The host first recognizes a device has

been plugged in because the device will send a high signal on either the D+ or D- wire to the root

hub, which subsequently notifies the host. The host then sends a USB reset signal to the device

through the hub. During the reset, the device will notify the host if it supports high speed by

sending a high signal on D-. Once this step is complete, the device is ready to receive control

transfers from the host on endpoint zero (p. 94). In his book, Advanced PIC Microcontroller

Projects in C, Ibrahim (2011) explains that the next thing the host does is send a Get Descriptor

command to the device to determine the device’s maximum packet size. After learning of the

devices maximum packet size, the host gives the device a unique address and sends a Set

Address request to the device. Using the newly assigned address, the host sends the Get

Descriptor request again because the first time it stopped after it found the maximum packet size.

The second request allows the host to learn the device manufacturer, type of device, and

maximum control packet size (Chap. 8, Enumeration, para. 1). The next command the host sends

is to get the device’s configuration data which includes descriptors for interfaces or other vendor

defined descriptors as well as the endpoint details for the given interfaces. Axelson (2015)

describes the final steps of enumeration mentioning that once the device responds to the host

with configuration data, the host uses the data to find the best match for a driver to manage

further device communications and vendor defined commands (p. 95-96).

Windows Driver Foundation

Page 13: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 13

The book Developing Drivers with Windows Driver Foundation written by Orwick and

Smith (2007) defines the Windows Driver Foundation (WDF) as a set of tools called frameworks

for developing Windows drivers. The two frameworks included in the WDF are the User Mode

Driver Framework (UMDF) and the Kernel Mode Driver Framework (KMDF) (Chap. 1 para. 4).

Belevsky and Pavlov (2008) explain that user mode drivers exist to increase system security,

stability, and fault tolerance by limiting the driver’s access to the core of the operating system. A

kernel mode driver allows direct access to user memory including the buffers used for passing

data (Chap. 6 para. 3,5).

The WDF frameworks consist of a library of objects used to interface with the operating

system for device input and output (Orwick & Smith, 2007, Kernel Objects and Data Structures

para. 1). In his book Windows 7 Device Driver, Reeves (2010) describes objects in the context of

computer programming by explaining that the objects are a digital representation of either a

physical entity or conceptual idea. The blueprint for the object is called a class and it defines the

storage of attributes and functions which represent the digital object. When a class is utilized in a

project, it behaves as a template for creating objects (Chap. 1 para. 2). Orwick and Smith (2007)

explain that objects are used in the WDF to represent common driver concepts like a devices, I/O

requests, or queues. Drivers communicate with devices through these WDF objects rather than

passing data to the operating system directly (Chap. 5, para. 1). The objects that make up the

Windows Driver Foundation are arranged in a hierarchy with the WDFDRIVER object as the

root (Reeves, 2010).

Conclusion

There is a distinct path that data follows as it passes from the device to the host. Details

regarding how data passes between a device and a host can be found in a variety of books,

Page 14: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 14

websites, and other publications. There are multiple steps involved in passing data between a

device and a host. The detail of literature allows readers to gain a thorough comprehension of the

USB communications procedures.

Chapter 3: Methodology and Design

Introduction to the Chapter

The main question being answered by this research paper is: How to write a Windows

USB driver for the PIC microcontroller? To answer this question, the research covered will focus

on resolving the answers to several sub questions, such as: What is a driver? What are the

fundamental requirements of a driver? What is the development environment for writing a

driver? How do applications communicate with a driver? What are the fundamental

requirements of a USB device? By understanding the answers to these sub questions, readers

with a basic understanding of object oriented programming should be able to develop a simple

driver for a PIC microcontroller USB device and the Windows operating system. This paper

utilizes a qualitative approach and the action methodology.

Body Paragraphs

There are many books written on the topic of USB devices and Windows software

development. The literature describes in detail much of the communication between USB

devices and the Windows operating system. In regards to Windows defined software libraries and

functions, the Microsoft Software Developer Network website will be used to reference

unfamiliar functions. Where a lack of clear instructions exists, an analysis of open source

software will be conducted utilizing the Microsoft Visual Studio 2015 integrated development

environment. Because complex and unnecessary code can complicate learning and debugging

(Martin, 2008), an emphasis will be placed on obtaining clean, concise sample code and

Page 15: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 15

removing any unused libraries, functions, and parameters. Data will be gathered by utilizing the

Visual Studio 2015 debugging tools, Windows event viewer, and registry editor. To ensure that a

working USB device has been created, testing will be documented using screen captures, photos

of the device, videos, and source code. The PIC18F45K50 microcontroller from Microchip

Technologies LLC. will be utilized as a test USB device using firmware included with the

MPLAB integrated development environment. A button will be connected to the microcontroller

on pin RB4 to test input to the Windows operation system and an LED will be connected to pin

RD3 to test output.

What is a driver? The book, “Developing drivers with the Microsoft Windows Driver

Foundation” will be the main resource in answering this question. The information derived from

the book will help clarify exactly where the data processing of a driver ends and where the

application takes control. This material will also cover the different varieties of drivers and under

what circumstances they should be used.

What are the fundamental requirements of a driver? The literature covers driver

requirements on an abstract basis. To get a deeper understanding of the specific functions and

code required by a driver, driver templates found in the Visual Studio library or online can be

utilized as a supplement to the books. Using the literature as a guide to the source code of a

driver, any code found to be irrelevant to the device hardware setup will be removed. This will

help to narrow down the driver to its most basic parts so that it can be better understood and to

mitigate the chance of software errors and reduce the time required for debugging.

What is the development environment for writing a driver? A major aspect of writing any

sort of code is the development environment. Reviewing the Microsoft Software Developer

Network will be essential to ensure that a proper Windows configuration is set up to write and

Page 16: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 16

deploy a driver for testing. Besides ensuring correct environment and settings for writing the

driver, a specific setup will also be required for writing firmware to the microcontroller. This will

require a review of Microchip’s website to ensure all the software has been properly installed and

that code can be written to the device.

What is required to be defined in the firmware to allow device communication to occur with a

host? A combination of data sheets and the book titled “An Introduction to USB and USB

Programming on Microchip Devices” will help outline the locations in firmware code where a

definition of the device can be created for sharing with a host.

What are the fundamental requirements of a USB device? The book, “USB Complete” by

Jan Axelson will help identify the hardware and software requirements of a USB device. This

book covers USB device communication starting from the electronic signals passing through a

USB cable up to the methods available for applications to retrieve data from the device driver

(Axelson, 2015). To send data to the PC a physical connection needs to exist. Knowing which

wires of the USB cable pass data and which provide power is important to ensure that data is

being passed correctly and no parts are damaged. By reviewing manufacturer data sheets and

using a multimeter to check signals, the correct USB cable configuration can be connected to a

device.

How do applications communicate with a driver? Steps must be taken to ensure USB

device drivers are successfully communicating with their intended applications within the

operating system. If the device is meant to be used as a keyboard, then will it only work with an

application that is looking for keyboard devices to connect to? A device can be made to be

recognized by the Windows operating system but can that same device communicate with any

Page 17: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 17

application? How does an application define the user input it is seeking? To find answers to these

questions, a review of additional books and online materials is required.

Conclusion

Once the results of the research have been accumulated the process for writing a driver

can still be obscured if it is not correctly presented. To ensure that it is organized in an

understandable way, the data will be presented starting with an explanation of the main question.

This will be followed by a summary of results of the research on the sub questions. A power

point presentation will be utilized to document the process of developing a driver. Source code,

images, and video will be displayed to show the process of writing firmware to a device, device

enumeration by the operating system, and finally, device interaction with a Windows application.

Chapter 4: Results of the Study

Introduction

Devices are a requirement for interfacing with a computer to send or receive data

(Reeves, 2010, Introduction para. 1). Devices are made by different manufacturers utilizing

various types of firmware code to control device functions (Ibrahim, 2011, Chap 8 Device

Descriptors). To make a device usable by a Windows operating system, software developers must

create a device driver. This paper aims to address the issue with the main question: How to write

a Windows USB driver for the PIC microcontroller? To answer this major question, five sub

questions were devised: What is a driver? What are the fundamental requirements of a driver?

What is the development environment for writing a driver? How do applications communicate

with a driver? What are the fundamental requirements of a USB device? By answering these

questions, it should become clear what the process is for writing a Windows driver.

Page 18: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 18

What is a driver?

The MSDN website defines a driver as follows:

“In the most fundamental sense, a driver is a software component that lets the operating

system and a device communicate with each other. For example, suppose an application needs to

read some data from a device. The application calls a function implemented by the operating

system, and the operating system calls a function implemented by the driver. The driver, which

was written by the same company that designed and manufactured the device, knows how to

communicate with the device hardware to get the data. After the driver gets the data from the

device, it returns the data to the operating system, which returns it to the application.” (What is a

Driver?, 2016, para. 1)

There are different kinds of drivers. For Windows, Orwick and Smith (2007) describe

kernel mode drivers and user mode drivers. Kernel mode drivers are written for maximum

control. They give the driver full access to underlying system commands. This allows

programming of drivers with unrestricted access to operating system components. However, if

there are any errors in the driver code, a kernel mode driver could cause applications or the host

operating system itself to crash. User mode drivers are not as versatile as kernel mode drivers

because Windows set of functions available to a user mode driver is less than a kernel mode

driver. This makes user mode drivers safer for an operating system (Chap. 2, Core Windows

Architecture, para. 2).

Besides the different modes of drivers, Axelson (2015) tells readers that Windows also

maintains a set of generic drivers for devices. For example, if a device is programmed with

firmware that defines it as a human interface device, then when the device is connected to a host,

Page 19: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 19

Windows will automatically give it a premade generic human interface driver. The firmware can

even define a device to belong to a specific type of HID class such as a game controller, joystick,

mouse, or keyboard. Windows has another generic driver called WinUSB. If a device is set to use

WinUSB, then Windows will assign it a WinUSB driver. Like HID drivers, Windows has

predefined functions which can be utilized by applications to access hardware (pg. 149).

What are the fundamental requirements of a driver?

According to Orwick and Smith (2007), Microsoft provides a software development

library called the Windows Driver Kit (WDK). As part of the development kit, template driver

projects are included as a foundation for building either user mode or kernel mode drivers (Chap.

1 Getting Started with Driver Development, para.1). The kernel mode driver template for USB

devices contains three main files called Device.c, Driver.c, and Queue.c. Each file has a

matching header file used to define functions and variables used by other parts of the driver as

well as the declarations of framework callback functions. The main template files contain the

basic functions required for a device driver. They include, DriverEntry, EvtDeviceAdd,

CreateDevice, EvtDevicePrepareHardware, and QueueInitialize. Also included in the template

are a Public.h header file which contains a GUID used by applications to interface with the

driver and an INF file. Axelson (2015) states that the INF file contains the information required

by a driver to detect its specific hardware device. Specifically, within the INF file a device PID

and VID must be defined (pg. 234). Once this is defined to match the PID and VID of the

firmware, the driver can be compiled and installed on a host. The device can now be paired with

a driver.

Though a device may be recognized by the system, the applications still cannot

communicate with the device. This is because the driver template provided by the WDK is not

Page 20: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 20

yet handling the callback function for input or output. According to Orwick and Smith, the driver

framework receives requests form the applications and passes them to the driver. The driver must

tell the framework how it wants to handle the incoming request. This is done with a callback

function (Chap. 4, KMDF Overview, para. 6). For example, if a host application has input or a

command for a device, the framework looks for the “EVT_WDF_IO_QUEUE_IO_WRITE”

callback function within the driver code (EVT_WDF_IO_QUEUE_IO_WRITE callback

function, 2016). By declaring an EVT_WDF_IO_QUEUE_IO_WRITE callback function in the

Queue.h file, an EvtIOWrite function can be added to Queue.c to handle incoming requests to

write to the device.

Once the driver has retrieved the request from the application, it can send it to a device

using a pipe. According to the Microsoft Developer Network website, to create a pipe, in the

EvtDevicePrepareHardware function, two WDF functions must be added. They are

WdfUsbTargetDeviceGetInterface and WdfUsbInterfaceGetConfiguredPipe. The

WdfUsbTargetDeviceGetInterface function returns a device interface. The interface can be used

to retrieve pipes using the WdfUsbInterfaceGetConfiguredPipe function (Working with USB

Pipes, 2016) (Working with USB Interfaces, 2016). Once a pipe has been retrieved, it can be

used in the EvtIOWrite callback function to write data to the device by passing the pipe and data

passed by an application as parameters to the WdfUsbTargetPipeWriteSynchronously function

(WdfUsbTargetPipeWriteSynchronously, 2016).

What is the development environment for writing a driver?

Writing a Windows driver requires a set of software programs for development and

testing. Orwick and Smith (2007) explain that one of the first tools required to get started is the

Windows Driver Kit (WDK). The Windows Driver Kit has a set of essential tools, predefined

Page 21: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 21

functions, and templates for creating Windows drivers (Getting Started with Driver

Development, para. 1). Besides a Windows operating system, one of the prerequisites for

installing the WDK is the Microsoft Visual Studio Integrated Development Environment (IDE)

(Windows Driver Kit, 2016).

Orwick and Smith (2007) warn that when testing a driver, it is a good practice to have the

development environment separated from the testing environment. Kernel mode drivers have

access to a part of the operating system that can cause errors and possibly irreversible damage to

the system if errors in the code exist. For this reason, it is recommended that a second computer

is used for driver testing and debugging (Getting Started with Driver Development, para. 4). To

mitigate that risk, one solution is to set up a virtual machine on the development computer. A

virtual machine is software that simulates an operating system. VMware, a developer of virtual

machines, wrote a white paper to describe some of the benefits of virtual machines. The white

paper explains that virtual machines are beneficial because they allow developers to quickly test

code without having to have a separate computer to test the code. Instead, the virtual machine

can be loaded right on the local machine while simultaneously using the developing operating

system to make quick changes to errors in code and redeploy (VMware, 2005). The VMware

virtual machine has a set of tools which allow the user to copy and paste items into the virtual

machine as well awareness of USB devices connected to the development operating system.

On the hardware side, the MPLABX IDE is required for programming a Microchip

device such as the PIC18F45K50. The IDE allows users to create edit, compile, test and debug

source code (Ibrahim, 2014, Chap. 3 para. 6). The website for MPLABX describes a useful set of

software available for the IDE called the Microchip Libraries for Applications (MLA). The MLA

Page 22: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 22

has sample firmware for common Microchip devices as well as applications for testing the

firmware after it has been loaded onto a device (Microchip Libraries for Applications, 2016).

How do applications communicate with a driver?

After completing the code for a driver with the capability of writing data to device, the

driver must be tested. For an application to communicate with a driver, it must issue a read or

write command using a handle to a device connected to the host. Getting a handle to the device

requires a few steps. According to Axelson (2015),the process starts when a Globally Unique

Identifier (GUID) variable is created and assigned a value matching that of the device class to

connect to. Next, the application gets a list of all the connected devices with a matching GUID

by issuing the SetupDiGetClassDevs function. Subsequently, the SetupDiEnumDeviceInterfaces

function is used to get a device interface by specifying the index of the device from the list

returned by the SetupDiGetClassDevs function. Once retrieved, the interface can be checked for

a matching vendor ID and product ID. If it doesn’t match, the function is called again using the

next higher index until a desired device interface is found. The SetupDiGetDeviceInterfaceDetail

function is used to retrieve a path to the device. The path is then used to create a handle to the

device using the CreateFile function (pg. 249-256). Once the handle has been created, it can be

used as a means for reading or writing data to a device by passing it as a parameter in the

WriteFile or ReadFile function. The other parameter in the function is a buffer for the data that is

being read or written. To write data, the buffer must be filled with data prior to calling the write

function.

What are the fundamental requirements of a USB device?

Axelson (2015) explained several hardware requirements for USB devices in the book

USB Complete. One of the first requirements is a chip capable of controlling communications

Page 23: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 23

with a host. The chip must have firmware loaded on it to allow communication to occur (pg. 25).

Some PIC microcontrollers like the PIC18F45K50 are capable of USB communication

(28/40/44-Pin, 2014, p. 1). The firmware for PIC devices is written using the MPLABX IDE

(Ibrahim, 2014, Chap. 3 para. 6). Ibrahim (2011) describes that a device requires several

descriptors be defined in the device firmware for the device to connect properly. The

configuration descriptor describes device power requirements and the number of interfaces on

the device. There is also an interface descriptor which defines the interface class and number of

endpoints. The last descriptor required is the endpoint descriptor which defines the address of an

endpoint and the maximum packet size that the endpoint can read (Ibrahim, 2011, Chap 8 Device

Descriptors). These descriptors are used by the driver to direct input and output to and from the

device.

Conclusion

It can now be seen that in order to write and test a driver there are several main

requirements. First, an environment must be set up to write and test the driver and the firmware.

Then the device must be loaded with firmware that properly defines the way the device is to

function. After that, a driver must be written for applications to be able to communicate with the

device. The driver should contain callback functions so that an application can communicate

with a driver. Finally, the driver must be tested using an application that has the required

functions to create a connection to the device.

Chapter 5: Summary and Discussion

Introduction

Page 24: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 24

A computer can communicate with hardware devices using a driver. This paper addresses

the procedure of developing a device driver for the Windows operating system. There are

different types of Windows devices. This paper discusses the development of drivers for USB

devices. The major question asked by this paper is: How to write a Windows USB driver for the

PIC microcontroller? This main question can be answered by resolving five sub-questions: What

is a driver? What are the fundamental requirements of a driver? What is the development

environment for writing a driver? How do applications communicate with a driver? What are the

fundamental requirements of a USB device? The answers to all these questions will give readers

an understanding of the basic requirements of a simple device driver.

Statement of Problem

Computer operating system requires user input and output to be fulfil its purpose. For this

to happen, devices require a driver to pass communications to the applications in the operating

system. This issue led me to find a microcontroller that would offer potential for customization

and to the major research question: How to write a Windows USB driver for the PIC

microcontroller?

Review of Methodology

To understand how to write a driver for the Windows operating system, several methods

were used. Literature from books and online resources were used to gain a general understanding

of the requirements of a driver. The book USB Complete by Jan Axelson (2015) provided details

about how electronic devices communicate with the operating system (pg. 234). The Microsoft

Developer Network website included descriptions of various functions used in the driver code.

The descriptions included details about where the function should be located within the code and

what parameters were required for the functions. At the application level, there was a need to

Page 25: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 25

identify the specific device for USB communication. The Microchip Technology firmware

source code provided the information required for the operating system to identify the device as

well as the size of the data block that it uses as input and output.

Summary of Results

The sub-questions were effective at describing the requirements of a Windows USB

device driver.

Sub Question One

To really understand the process of writing a driver for the Windows operating system, it

is important to know the answer to the question: “What is a driver?” There are drivers for many

computer peripherals including USB devices. Orwick and Smith (2007) describe two specific

types of drivers, kernel mode drivers and user mode drivers (Chap. 2, Core Windows

Architecture, para. 2). The operating system uses these drivers to handle data passed from

electronic devices to the operating system.

Sub Question Two

In order to understand the answer to the second sub-question, “What are the fundamental

requirements of a driver?” Windows Driver Template files were viewed to see the essential

elements of the driver. The template contained 3 main files, Device.c, Driver.c, and Queue.c.

Within these files, there were several required functions, DriverEntry, EvtDeviceAdd,

CreateDevice, EvtDevicePrepareHardware, and QueueInitialize. These functions contain several

lines of code each and give the driver the ability to pass data between the device and the

operating system applications. One additional file needs added to give the driver write capability.

That function is the “EVT_WDF_IO_QUEUE_IO_WRITE”

(EVT_WDF_IO_QUEUE_IO_WRITE callback function, 2016). The INF file is also included in

Page 26: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 26

the template and helps the operating system match the driver to the device when the device is

plugged in (Axelson, 2015, pg. 234).

Sub Question Three

Writing any type of software requires special software. The second sub-question asks:

“What is the development environment for writing a driver?” Orwick and Smith (2007) describe

the Windows Driver Kit (WDK) as one tool that is required to write Windows drivers. In order to

use the development kit, the Microsoft Visual Studio program is required. This program is like a

word processor with special tools used for writing computer software. (Windows Driver Kit,

2016).

Sub Question Four

Even though a driver for a device may exist, applications must have access to the driver

in order to communicate with a device. The answer to the question “How do applications

communicate with a driver?” will resolve the issue by describing what functions an application

must have to pass data to a device driver. Axelson (2015) describes that applications get a list of

available devices for communication by using the “SetupDiGetClassDevs” function. The

function returns a list of devices which the application can sift through until it finds one with a

Vendor ID and Product ID matching the device it wants to connect with (pg. 249-256). Once a

device has been found, it can have data or commands written to it using the WriteFile function.

Or data can be read from it using the ReadFile function.

Sub Question Five

The final sub-question is: “What are the fundamental requirements of a USB device?”

Axelson (2015) explained that a USB device requires a microchip with firmware installed (pg.

25). The firmware holds the definition of the device so the host can determine which driver to

Page 27: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 27

assign to it once it is connected. Ibrahim (2011) describes a type of data block called a descriptor

as an item included in the device firmware. The descriptors define the device type, GUID,

Vendor ID, Product ID, as well as the addresses for device input and output and maximum

message size for those addresses (Ibrahim, 2011, Chap 8 Device Descriptors).

Relationship of Research to the Field

The literature describes many aspects of USB development which were confirmed

through the project. Jan Axelson (2015) describes the requirement that a driver connect to a

device using a GUID and an application connect using a vendor ID and a product ID (pg. 249-

256). By creating an actual USB device using a PIC18 microcontroller, this became very clear as

the driver would not install correctly if the GUID was incorrect, and an application would not

connect to the device when the vendor ID and product ID were not properly defined.

Discussion of Results

A review of the literature regarding driver development shows that there are several steps

for communication to occur between a USB device and a Windows application. Often, the

literature focuses on a single step of USB communication, such as USB device firmware,

microcontroller programming, operating system structure, or driver frameworks. This paper adds

to the literature by showing how all the steps connect to allow USB communication. Rather than

focus on a single step, the paper shows how data originates at either the host or the device and is

passed from one place to the next until it arrives at its destination.

Conclusion

This paper addressed the question: “How to write a Windows USB driver for the PIC

microcontroller?” By answering the sub-questions, it can be seen that devices communicate to a

host through a few steps. First, the device must be loaded with firmware which holds the

Page 28: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 28

definition of what type of device it is, and how it passes data to the computer. Then the device

must have a driver written for it, so that it can be detected when it is plugged into the computer.

The driver must have an INF file which defines the device it is matched to by a GUID, Vendor

ID, and Product ID. Once a device is successfully connected, a driver must contain the proper

functions so that applications can pass data to and from the device. The literature helped to

outline all the steps required for this USB communication to occur. This paper adds to the

literature by providing a detailed description of how the communication occurs from start to

finish.

References

Axelson, J. (2015). USB complete: The developer's guide. Madison, WI: Lakeview Research

LLC.

Belevsky, P. & Pavlov S. (2008). Windows® Embedded CE 6.0 Fundamentals. Available from

https://www.safaribooksonline.com/library/view/windows-embedded-ce/9780735626256/

Catsoulis, J. (2005). Designing Embedded Hardware, 2nd Edition. Available from

Page 29: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 29

https://www.safaribooksonline.com/library/view/designing-embedded-hardware/

0596007558/ch11.html

Eliasz, A. (2016). An Introduction to USB and USB Programming on Microchip Devices. The

Internet Technical Bookshop.

EVT_WDF_IO_QUEUE_IO_WRITE callback function. (2016) Retrieved November 26, 2016

from

https://msdn.microsoft.com/en-us/library/windows/hardware/ff541813(v=vs.85).aspx

Ibrahim, D. (2014). PIC microcontroller projects in C: Basic to advanced. Available from

https://www.safaribooksonline.com/library/view/advanced-pic-microcontroller/

9780750686112/

Ibrahim, D. (2014). PIC microcontroller projects in C: Basic to advanced. Available from

https://www.safaribooksonline.com/library/view/pic-microcontroller-projects/

9780080999241/

McDowell, S. & Seyer, M. D. (1998) USB Explained. Available from

https://www.safaribooksonline.com/library/view/usb-explained/9780132442350/

Microchip Libraries for Applications. (2016). Retrieved on November 16, 2016 from

http://www.microchip.com/mplab/microchip-libraries-for-applications

Microchip Technology Inc. (2012-2014). 28/40/44-Pin, Low-Power, High-Performance

Microcontrollers with XLP Technology Retrieved from

http://ww1.microchip.com/downloads/en/DeviceDoc/30000684B.pdf

Murphy, R. (09/14/2016). USB 101: An Introduction to USB 2.0. Retrieved from

http://www.cypress.com/documentation/application-notes/an57294-usb-101-introduction-

universal-serial-bus-20

Page 30: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 30

NaturalPoint Inc. (2016). https://naturalpoint.com/trackir/trackir5/. Retrieved from

https://naturalpoint.com/: https://naturalpoint.com/trackir/trackir5/

Net Applications.com. (2006-2016). operating-system-market-share. Retrieved from

netmarketshare: https://www.netmarketshare.com/operating-system-market-share.aspx?

qprid=10&qpcustomd=0

Orwick, P., & Smith, G. (2007). Developing Drivers with the Microsoft Windows Driver

Foundation. Available from https://www.safaribooksonline.com/library/view/developing-

drivers-with/9780735623743/

Rafiquzzaman, M. (2014). Fundamentals of Digital Logic and Microcontrollers, 6th Edition.

Available from https://www.safaribooksonline.com/library/view/fundamentals-of-

digital/9781118969304/

Reeves, R. D. (2010) Windows 7 Device Driver. Available from

https://www.safaribooksonline.com/library/view/windows-7-device/9780321670540/

Russinovich, M. E., Solomon, D. A., & Ionescu, A. (2012). Windows Internals (6th ed., Vol. 2).

Redmond, WA: Microsoft Press.

USB-IF (2000). Universal Serial Bus Specification. Retrieved from

http://www.usb.org/developers/docs/usb20_docs/

USB-IF (2011). Universal Serial Bus 3.0 Specification. Retrieved from

http://www.usb.org/developers/docs/documents_archive/

USB-IF (2013). Universal Serial Bus 3.1 Specification. Retrieved from

http://www.usb.org/developers/docs/documents_archive/

VMWare White Paper. (2005). Retrieved from http://www.vmware.com/pdf/dev_test.pdf

WDF Driver Development Guide. (2016, July 30). Retrieved November 14, 2016, from

Page 31: PICDriverResearch

Developing a Windows Driver for the PIC Microcontroller 31

https://msdn.microsoft.com/en-us/windows/hardware/drivers/wdf/index

WdfUsbTargetPipeWriteSynchronously method. (2016). Retrieved November 14, 2016, from

https://msdn.microsoft.com/library/windows/hardware/ff551163

What is a Driver? (2016) Retrieved November 26, 2016, from https://msdn.microsoft.com/en-

us/library/windows/hardware/ff554678(v=vs.85).aspx

Windows Driver Kit (WDK). (2016). Retrieved November 16, 2016 from

https://msdn.microsoft.com/en-us/library/windows/hardware/ff557573(v=vs.85).aspx

Working With USB Interfaces. (2016). Retrieved November 26,2016 from

https://msdn.microsoft.com/en-us/windows/hardware/drivers/wdf/working-with-usb-

interfaces

Working With USB Pipes. (2016). Retrieved November 26, 2016 from

https://msdn.microsoft.com/en-us/windows/hardware/drivers/wdf/working-with-usb-

pipes

How to Enumerate USB Pipes. (2016). Retrieved November 14, 2016, from

https://msdn.microsoft.com/en-us/library/windows/hardware/hh968306(v=vs.85).aspx