The I/O control driver is built as a module, can be used for controlling common peripherals, such as LED, push button, buzzer.
Copy io_control_dev to your ubuntu system, compile it with your own system setting (refer to Appendix 1 "Compiling Driver Module"), and copy the generated io_control.ko file to the board, use the following command to load the driver module:
$insmod io_control.ko
Now you can start to try the I/O control API demo (refer to Appendix 2 "Running API Demo").
The buzzer can be shut up via configuring the related I/O port. Config the script.fex as follows:
[lcd0_para] lcd_gpio_0 = port:PH15<0><0><default><default>
Then convert it into script.bin format by using fex2bin, and replace the earlier script.bin on the board. (for more info, refer to the document Prepare for Kernel and Drivers Porting Reboot the system to apply new configuration.
Config the kernel to include Dallas’s 1-wire(DS18B20) driver. Under the root directory, enter the following commnad:
#make menuconfig
(All the make menuconfig that follows in this document, is executed under root directory)
Config as follows:
Device Drivers ---> <*> Dallas's 1-wire support ---> 1-wire Bus Masters ---> <*> GPIO 1-wire busmaster 1-wire Slaves ---> <*> Thermal family implementation
Save and exit, re-compile the kernel:
#make uImage
Replace the earlier uImage on the board with the new generated uImage under arch/arm/boot/ directory via NFS. (for more info, refer to the document Prepare for Kernel and Drivers Porting
Config the script.fex as follows, add the [w1_para] setting:
[w1_para] w1_used = 1 w1_pin = port:PB10<1><default><default><default>
Then convert it into script.bin format by using fex2bin, and replace the earlier script.bin on the board. (for more info, refer to the document Prepare for Kernel and Drivers Porting
Reboot the system, insert the DS18B20 device.
Copy ds18b20_dev to your ubuntu system, compile it with your own system setting (refer to Appendix 1 "Compiling Driver Module"), and copy the generated w1-sun4i.ko file to the board, use the following command to load the driver:
$insmod w1-sun4i.ko
Enter the /sys/bus/w1/devices/w1_bus_master1 directory, there's a folder with the name preceding with "28-", which represents the DS18B20 device. The 28 means the current temperature sensor is DS18B20, the characters/numbers string follows stands for the device unique ID. Enter the folder, you should find it's device file named w1_slave, to get current temperature, enter this command on the terminal:
$cat w1_slave
As shown in the picture below:
Config the kernel to include I2C bus driver:
#make menuconfig Device Drivers ---> {*} I2C support ---> I2C Hardware Bus support ---> <*> Allwinner Technology SUNXI I2C interface
Save and exit. Comment out lines 914 to 918 of the i2c-sunxi.c file, which is located in drivers/i2c/busses directory, as follows:
914 /* else if (ret != num){ 915 printk("incomplete xfer (0x%x)\n", ret); 916 ret = -ECOMM; 917 //dev_dbg(i2c->adap.dev, "incomplete xfer (%d)\n", ret); 918 }*/
Save, and re-compile the kernel:
#make uImage
Replace the earlier uImage on the board with the new generated uImage under arch/arm/boot/ directory via NFS. (for more info, refer to the document <4. Prepare for Kernel and Drivers Porting>)
Our AT24/FM24 module can be used to test the I2C driver, which is connected to the I2C1 controller. Therefore, config the [twi1_para] setting in the script.fex as follows:
[twi1_para] twi1_used = 1 twi1_scl = port:PB18<2><default><default><default> twi1_sda = port:PB19<2><default><default><default>
Then convert it into script.bin format by using fex2bin, and replace the earlier script.bin on the board. (for more info, refer to the document Prepare for Kernel and Drivers Porting
Reboot the system.
For more info about testing the AT24/FM24 module, like reading/writing data, please refer to the document DVK521 User Manual and Appendix 2 "Running API Demo".
The A20 SPI is not natively supported by linux-sunxi-sunxi-3.4.61 kernel. You should copy the spi-sun7i.c file spi-sun7i.c to the drivers/spi directory in the kernel, and modify the related Makefile and Kconfig under the same directory.
Add the following line in Makefile:
obj-$(CONFIG_SPI_SUN7I) += spi-sun7i.o
Add the following line in Kconfig:
config SPI_SUN7I tristate "SUN7I SPI Controller" depends on ARCH_SUN7I help Allwinner Soc SPI controller,present on SUN7I chips. config SUN7I_SPI_NDMA bool "SUN7I SPI Normal DMA mode select" depends on SPI_SUN7I help This selects SPI DMA mode with DMA transfer Y select NDMA mode and N select DDMA mode
#make menuconfig Device Drivers ---> [*] SPI support ---> <*> SUN7I SPI Controller [*] SUN7I SPI Normal DMA mode select <*> DesignWare SPI controller core support <*> User mode SPI device driver support
Save and exit, re-compile the kernel:
#make uImage
Replace the earlier uImage on the board with the new generated uImage under arch/arm/boot/ directory via NFS. (for more info, refer to the document Prepare for Kernel and Drivers Porting
Our SPI module AT45DBXX DataFlash Board is connected to the SPI0 controller, therefore, config the [spi0_para], [spi_devices], and [spi_board0] settings in the script.fex as follows:
[spi0_para] spi_used = 1 spi_cs_bitmap = 1 spi_cs0 = port:PI10<2><default><default><default> spi_cs1 = port:PI14<2><default><default><default> spi_sclk = port:PI11<2><default><default><default> spi_mosi = port:PI12<2><default><default><default> spi_miso = port:PI13<2><default><default><default>
[spi_devices] spi_dev_num = 1
[spi_board0] modalias = "spidev" max_speed_hz = 12000000 bus_num = 0 chip_select = 0 mode = 3 full_duplex = 0 manual_cs = 0
Then convert it into script.bin format by using fex2bin, and replace the earlier script.bin on the board. (for more info, refer to the document Prepare for Kernel and Drivers Porting
Now the kernel and script.fex configuration for SPI device have completed, the last step is to load the io_control.ko driver module (refer to the previous section " Porting I/O Control Driver").
Reboot the system.
Now you can use the AT45DBXX DataFlash Board to test the SPI driver (refer to Appendix 2 "Running API Demo").
The LCD driver support has been included in linux-sunxi-sunxi-3.4.61, the driver file can be found on drivers/video/sunxi/lcd.
Check the kernel configuration, confirm that the driver is included:
#make menuconfig Device Drivers ---> Graphics support ---> {*} Support for frame buffer devices ---> <*> DISP Driver Support(sunxi) -*- Reserve memory block for sunxi/fb [*] Enable FB/UMP Integration <*> LCD Driver Support(sunxi) <*> HDMI Driver Support(sunxi)
Save and exit, re-compile the kernel:
#make uImage
Replace the earlier uImage on the board with the new generated uImage under arch/arm/boot/ directory via NFS. (for more info, refer to the document Prepare for Kernel and Drivers Porting
The A20 supports two channel video output, however, only LCD0 is available on Cubieboard, therefore, we connect the 7inch capacitive LCD to the LCD0 controller.
Config the script.fex, [dis_init] setting for display device initialization, and [lcd0_para] setting for LCD parameters (depending on the specifications of concrete LCD), as follows:
[disp_init] disp_init_enable = 1 disp_mode = 0 screen0_output_type = 1 screen0_output_mode = 4 screen1_output_type = 0 screen1_output_mode = 4 fb0_width = 1024 fb0_height = 768 fb0_framebuffer_num = 2 fb0_format = 10 fb0_pixel_sequence = 0 fb0_scaler_mode_enable = 0 fb1_width = 1024 fb1_height = 768 fb1_framebuffer_num = 2 fb1_format = 10 fb1_pixel_sequence = 0 fb1_scaler_mode_enable = 0 lcd0_backlight = 197 lcd1_backlight = 197 lcd0_bright = 50 lcd0_contrast = 50 lcd0_saturation = 57 lcd0_hue = 50 lcd1_bright = 50 lcd1_contrast = 50 lcd1_saturation = 57 lcd1_hue = 50
[lcd0_para] lcd_used = 1 lcd_x = 800 lcd_y = 480 lcd_dclk_freq = 33 lcd_pwm_not_used = 0 lcd_pwm_ch = 0 lcd_pwm_freq = 10000 lcd_pwm_pol = 0 lcd_max_bright = 240 lcd_min_bright = 64 lcd_if = 0 lcd_hbp = 215 lcd_ht = 1055 lcd_vbp = 34 lcd_vt = 1050 lcd_vspw = 3 lcd_hspw = 20 lcd_hv_if = 0 lcd_hv_smode = 0 lcd_hv_s888_if = 0 lcd_hv_syuv_if = 0 lcd_lvds_ch = 0 lcd_lvds_mode = 0 lcd_lvds_bitwidth = 0 lcd_lvds_io_cross = 0 lcd_cpu_if = 0 lcd_frm = 1 lcd_io_cfg0 = 0 lcd_gamma_correction_en = 0 lcd_gamma_tbl_0 = 0x0 lcd_gamma_tbl_1 = 0x10101 lcd_gamma_tbl_255 = 0xffffff lcd_bl_en_used = 1 lcd_bl_en = port:PH07<1><0><default><1> lcd_power_used = 1 lcd_power = port:PH08<1><0><default><1> lcd_pwm_used = 1 lcd_pwm = port:PB02<2><0><default><default> lcd_gpio_0 = port:PH15<0><0><default><default> lcd_gpio_1 = lcd_gpio_2 = lcd_gpio_3 = lcdd0 = port:PD00<2><0><default><default> lcdd1 = port:PD01<2><0><default><default> lcdd2 = port:PD02<2><0><default><default> lcdd3 = port:PD03<2><0><default><default> lcdd4 = port:PD04<2><0><default><default> lcdd5 = port:PD05<2><0><default><default> lcdd6 = port:PD06<2><0><default><default> lcdd7 = port:PD07<2><0><default><default> lcdd8 = port:PD08<2><0><default><default> lcdd9 = port:PD09<2><0><default><default> lcdd10 = port:PD10<2><0><default><default> lcdd11 = port:PD11<2><0><default><default> lcdd12 = port:PD12<2><0><default><default> lcdd13 = port:PD13<2><0><default><default> lcdd14 = port:PD14<2><0><default><default> lcdd15 = port:PD15<2><0><default><default> lcdd16 = port:PD16<2><0><default><default> lcdd17 = port:PD17<2><0><default><default> lcdd18 = port:PD18<2><0><default><default> lcdd19 = port:PD19<2><0><default><default> lcdd20 = port:PD20<2><0><default><default> lcdd21 = port:PD21<2><0><default><default> lcdd22 = port:PD22<2><0><default><default> lcdd23 = port:PD23<2><0><default><default> lcdclk = port:PD24<2><0><default><default> lcdde = port:PD25<2><0><default><default> lcdhsync = port:PD26<2><0><default><default> lcdvsync = port:PD27<2><0><default><default>
Then convert it into script.bin format by using fex2bin, and replace the earlier script.bin on the board. (for more info, refer to the document <4. Prepare for Kernel and Drivers Porting>)
Reboot the system, the LCD should be ready to work.
Our capacitive touch screen integrates FT5206 as the touch controller, and the related driver file is ft5x_ts.c. Unfortunately the original ft5x_ts.c in linux-sunxi-sunxi-3.4.61 kernel doesn’t support A20, therefore, copy the new ft5x_ts.c ft5x_ts.c to the drivers/input/touchscreen directory in kernel and replace the original one. Besides, the touch screen interrupt pin ctp_int_port requires GPIO interrupts, make sure the GPIO driver is included when configuring.
Config the Kernel to include touchscreen driver:
#make menuconfig Device Drivers ---> Input device support ---> [*] Touchscreens ---> <*> ft5x touchscreen driver Device Drivers ---> [*] GPIO Support ---> <*> GPIO Support for sunxi platform
Re-compile the kernel:
#make uImage
Replace the earlier uImage on the board with the new generated uImage under arch/arm/boot/ directory via NFS. (for more info, refer to the document Prepare for Kernel and Drivers Porting
Since the touch screen is connected to I2C1 controller, make sure the I2C driver has been ported (refer to the previous section "Porting I2C Bus Driver"). Config the [ctp_para],[ctp_list_para],and[gpio_para] setting in script.fex.
ctp_name:driver name ctp_twi_id:I2C controller which is actually used ctp_twi_addr:I2C device address (7bit) ctp_screen_max_x:touch panel resolution ctp_screen_max_y:touch panel resolution ctp_revert_x_flag:set 1 to revert x axis ctp_revert_y_flag:set 1 to revert y axis ctp_exchange_x_y_flag:set 1 to exchange x axis and y axis ctp_int_port:touch interrupt pin ctp_wakeup:touch wakeup pin ctp_io_port:interrupt pin configuration
According to the specifications and hardware connection of our 7inch capacitive LCD, config as follows:
[ctp_para] ctp_used = 1 ctp_name = "ft5x_ts" ctp_twi_id = 1 ctp_twi_addr = 0x38 ctp_screen_max_x = 800 ctp_screen_max_y = 480 ctp_revert_x_flag = 0 ctp_revert_y_flag = 1 ctp_exchange_x_y_flag = 0 ctp_firm = 1 ctp_wakeup = port:PB13<1><default><default><1> [ctp_list_para] ctp_det_used = 1 ft5x_ts = 1 gt82x = 0 gslX680 = 0 gt9xx_ts = 0 gt811 = 0 [gpio_para] gpio_pin_3 = port:PH07<6><default><default><default>
Then convert it into script.bin format by using fex2bin, and replace the earlier script.bin on the board. (for more info, refer to the document Prepare for Kernel and Drivers Porting
Connect the 7inch capacitive LCD, reboot the system, try to touch the icons on the screen.
VAG driver has been includes in the kernel, just config the script.fex directly:
[disp_init] disp_init_enable = 1 disp_mode = 0 screen0_output_type = 4 screen0_output_mode = 4 screen1_output_type = 0 screen1_output_mode = 4 fb0_width = 1024 fb0_height = 768 fb0_framebuffer_num = 2 fb0_format = 10 fb0_pixel_sequence = 0 fb0_scaler_mode_enable = 0 fb1_width = 1024 fb1_height = 768 fb1_framebuffer_num = 2 fb1_format = 10 fb1_pixel_sequence = 0 fb1_scaler_mode_enable = 0 lcd0_backlight = 197 lcd1_backlight = 197 lcd0_bright = 50 lcd0_contrast = 50 lcd0_saturation = 57 lcd0_hue = 50 lcd1_bright = 50 lcd1_contrast = 50 lcd1_saturation = 57 lcd1_hue = 50
Then convert it into script.bin format by using fex2bin, and replace the earlier script.bin on the board. (for more info, refer to the document <4. Prepare for Kernel and Drivers Porting>) Reboot the system, now the VGA can be used for displaying.
HDMI driver has been includes in the kernel, just config the script.fex directly:
[disp_init] disp_init_enable = 1 disp_mode = 0 screen0_output_type = 3 screen0_output_mode = 5 screen1_output_type = 0 screen1_output_mode = 4 fb0_width = 1024 fb0_height = 768 fb0_framebuffer_num = 2 fb0_format = 10 fb0_pixel_sequence = 0 fb0_scaler_mode_enable = 0 fb1_width = 1024 fb1_height = 768 fb1_framebuffer_num = 2 fb1_format = 10 fb1_pixel_sequence = 0 fb1_scaler_mode_enable = 0 lcd0_backlight = 197 lcd1_backlight = 197 lcd0_bright = 50 lcd0_contrast = 50 lcd0_saturation = 57 lcd0_hue = 50 lcd1_bright = 50 lcd1_contrast = 50 lcd1_saturation = 57 lcd1_hue = 50
Reboot the system, now the HDMI can be used for displaying.
#make menuconfig Device Drivers ---> <*> Multimedia support ---> <*> Video For Linux [*] CSI Driver Config for sun4i ---> <M> OmniVision OV7670 sensor support
Built the camera driver as module, save and exit.
Comment out the print messages in the s32 img_sw_para_to_reg(u8 type, u8 mode, u8 value) function in disp_layer.c file, which is under drivers/video/sunxi/disp directory.
Lines 95 to 99:
95 /* else { 96 DE_WRN("not supported yuv channel format:%d in " 97 "img_sw_para_to_reg\n", value); 98 return 0; 99 }*/
Lines 125 to 129:
125 /* else { 126 DE_WRN("not supported yuv channel pixel sequence:%d " 127 "in img_sw_para_to_reg\n", value); 128 return 0; 129 }*/
Lines 168 to 172:
168 /* else { 169 DE_WRN("not supported image0 pixel sequence:%d in " 170 "img_sw_para_to_reg\n", value); 171 return 0; 172 }*/
Line 175:
175 // DE_WRN("not supported type:%d in img_sw_para_to_reg\n", type);
Save, re-compile the kernel:
#make uImage
Compile the kernel modules:
#make modules
Install the kernel modules:
#make modules_install
The installation copies the compiled kernel module from the kernel source code to the ubuntu /lib/modules directory.
The related driver module files include: videobuf-core.ko, videobuf-dma-contig.ko, sun4i_csi1.ko, ov7670.ko, which are located respectively in:
videobuf-core.ko, videobuf-dma-contig.ko: /lib/modules/3.4.61+/kernel/drivers/media/video ov7670.ko: /lib/modules/3.4.61+/kernel/drivers/media/video/sun4i_csi/device sun4i_csi1.ko: /lib/modules/3.4.61+/kernel/drivers/media/video/sun4i_csi/csi1
Replace the earlier uImage on the board with the new generated uImage under arch/arm/boot/ directory via NFS. (for more info, refer to the document Prepare for Kernel and Drivers Porting
Copy the above 4 driver files to the board, and install them in order:
$insmod videobuf-core.ko $insmod videobuf-dma-contig.ko $insmod ov7670.ko $insmod sun4i_csi1.ko
Note: please pay attention to the installing order, camera driver should be installed before sun4i_csi1.ko.
Since our OV7670 camera is connected to the CSI1 controller, config the [csi1_para] and [camera_list_para] setting in script.fex. The suffix _b in the parameter name indicates that this is a secondary camera parameter while two cameras were connected to the same CSI.
The parameters are interpreted as follows:
csi_used = xx:enable/disable csi0 or csi1 csi_mode = xx:CSI receiver buffer mode: 0:a stand-alone buffer for each CSI receiver 1:a shared buffer for both CSI receiver csi_dev_qty = xx:CSI device quantity, 1 or 2 csi_stby_mode = xx:standby power statue 0:power on when standby 1:power off when standby csi_mname = “xxx”: CSI module name, matches with the driver, valid option includes: ov7670/gc0308/gt2005/hi704/sp0338/mt9m112/gc0307/mt9m113/mt9d112/hi253/ov5640 csi_twi_id = xx:I2C csi_twi_addr = xx:I2C address csi_if = xx:interface timing: 0:8bit data line, with Hsync,Vsync 1:16bit data line, with Hsync,Vsync 2:24bit data line, with Hsync,Vsync 3:8bit data line, BT656 embedded sync, single-channel 4:8bit data line, BT656 embedded sync, dual-channels 5:8bit data line, BT656 embedded sync, four-channels csi_vflip = xx:video vertical flip 0:normal 1:flip csi_hflip = xx:video horizontal flip 0:normal 1:flip csi_iovdd = "", csi_avdd = "", and csi_dvdd = "": power supply of the camera module's IO, Analog, and Core. "axp20_pll": powering from AXP20 LDO3 "axp20_hdmi": powering from AXP20 LDO4 "": powering from other source csi_flash_pol = xx:flash polarity for cameras that feature flash IO control 0: flash lights when IO low level 1: flash lights when IO high level csi_pck = xx:GPIO configuration for clock signal from module to CSI csi_ck = xx:GPIO configuration for clock signal from CSI to module csi_hsync = xx:GPIO configuration for horizontal sync signal from module to CSI csi_vsync = xx:GPIO configuration for vertical sync signal from module to CSI csi_d0 = xx to csi_d15 = xx:GPIO configuration for 8bit/16bit data from module to CSI csi_reset = xx:GPIO configuration for module reset csi_power_en = xx:GPIO configuration for module power, high active by default csi_stby = xx:GPIO configuration for module standby csi_af_en = xx:GPIO configuration for module AF power
The details configuration:
[csi1_para] csi_used = 1 csi_dev_qty = 1 csi_stby_mode = 0 csi_mname = "ov7670" csi_if = 0 csi_iovdd = "axp20_pll" csi_avdd = "" csi_dvdd = "" csi_vol_iovdd = 2800 csi_vol_dvdd = csi_vol_avdd = csi_vflip = 1 csi_hflip = 0 csi_flash_pol = 1 csi_facing = 1 csi_twi_id = 1 csi_twi_addr = 0x42 csi_pck = port:PG00<3><default><default><default> csi_ck = port:PG01<3><default><default><default> csi_hsync = port:PG02<3><default><default><default> csi_vsync = port:PG03<3><default><default><default> csi_d0 = port:PG04<3><default><default><default> csi_d1 = port:PG05<3><default><default><default> csi_d2 = port:PG06<3><default><default><default> csi_d3 = port:PG07<3><default><default><default> csi_d4 = port:PG08<3><default><default><default> csi_d5 = port:PG09<3><default><default><default> csi_d6 = port:PG10<3><default><default><default> csi_d7 = port:PG11<3><default><default><default> csi_reset = port:PH13<1><default><default><0> csi_power_en = port:PH16<1><default><default><0> csi_stby = port:PH19<1><default><default><0>
[camera_list_para] camera_list_para_used = 1 ov7670 = 1 gc0308 = 0 gt2005 = 0 hi704 = 0 sp0838 = 0 mt9m112 = 0 mt9m113 = 0 ov2655 = 0 hi253 = 0 gc0307 = 0 mt9d112 = 0 ov5640 = 0 gc2015 = 0 ov2643 = 0 gc0329 = 0 gc0309 = 0 tvp5150 = 0 s5k4ec = 0 ov5650_mv9335 = 0 siv121d = 0 gc2035 = 0
Then convert it into script.bin format by using fex2bin, and replace the earlier script.bin on the board. (for more info, refer to the document Prepare for Kernel and Drivers Porting
Connect the OV7670 camera module and the LCD to the board, reboot the system.
Now you can start to try the camera API demo (refer to Appendix 2 "Running API Demo").
The provided xx.ko files under Driver is compiled to run on our system image only.
If the drivers are going to being loaded on your own system, they need to be re-compiled according to you system kernel path.
Use the io_control_dev.ko for demonstration.
1.1 Copy the io_control_dev to ubuntu, assume the target directory is /home/waveshare/cubieboard2/waveshare_demo/driver . Modify the files permission:
#cd /home/waveshare/cubieboard2/waveshare_demo/driver/io_control_dev
#chmod 777 ./*
1.2 Modify the Makefile
#vi Makefile
Assign the KERNELDIR according to your actual kernel path.
1.3 Clear the old files
#make clean
1.4 Compile
#make
An error might occur while compiling:
io_control.c:1:23: fatal error: linux/init.h: No such file or directory compilation terminated. make: *** [modules] Error 1
As shown in the picture below:
It is caused by the different kernel version, can be just omitted.
Copy the new generated io_control.ko file to your own system and load it.
When the driver has been loaded, you can start to try the API demo.
Copy the API source code to your ubuntu, and modify the files permission:
#chmod 777 ./*
Execute the following command to compile:
#make
Then copy the executable file to the board, say, "test_led", use the following command to run it:
#./ test_led